Source Code Cross Referenced for DeviceEmul.java in  » 6.0-JDK-Modules » j2me » com » sun » midp » jsr82emul » Java Source Code / Java DocumentationJava Source Code and Java Documentation

Java Source Code / Java Documentation
1. 6.0 JDK Core
2. 6.0 JDK Modules
3. 6.0 JDK Modules com.sun
4. 6.0 JDK Modules com.sun.java
5. 6.0 JDK Modules sun
6. 6.0 JDK Platform
7. Ajax
8. Apache Harmony Java SE
9. Aspect oriented
10. Authentication Authorization
11. Blogger System
12. Build
13. Byte Code
14. Cache
15. Chart
16. Chat
17. Code Analyzer
18. Collaboration
19. Content Management System
20. Database Client
21. Database DBMS
22. Database JDBC Connection Pool
23. Database ORM
24. Development
25. EJB Server geronimo
26. EJB Server GlassFish
27. EJB Server JBoss 4.2.1
28. EJB Server resin 3.1.5
29. ERP CRM Financial
30. ESB
31. Forum
32. GIS
33. Graphic Library
34. Groupware
35. HTML Parser
36. IDE
37. IDE Eclipse
38. IDE Netbeans
39. Installer
40. Internationalization Localization
41. Inversion of Control
42. Issue Tracking
43. J2EE
44. JBoss
45. JMS
46. JMX
47. Library
48. Mail Clients
49. Net
50. Parser
51. PDF
52. Portal
53. Profiler
54. Project Management
55. Report
56. RSS RDF
57. Rule Engine
58. Science
59. Scripting
60. Search Engine
61. Security
62. Sevlet Container
63. Source Control
64. Swing Library
65. Template Engine
66. Test Coverage
67. Testing
68. UML
69. Web Crawler
70. Web Framework
71. Web Mail
72. Web Server
73. Web Services
74. Web Services apache cxf 2.0.1
75. Web Services AXIS2
76. Wiki Engine
77. Workflow Engines
78. XML
79. XML UI
Java
Java Tutorial
Java Open Source
Jar File Download
Java Articles
Java Products
Java by API
Photoshop Tutorials
Maya Tutorials
Flash Tutorials
3ds-Max Tutorials
Illustrator Tutorials
GIMP Tutorials
C# / C Sharp
C# / CSharp Tutorial
C# / CSharp Open Source
ASP.Net
ASP.NET Tutorial
JavaScript DHTML
JavaScript Tutorial
JavaScript Reference
HTML / CSS
HTML CSS Reference
C / ANSI-C
C Tutorial
C++
C++ Tutorial
Ruby
PHP
Python
Python Tutorial
Python Open Source
SQL Server / T-SQL
SQL Server / T-SQL Tutorial
Oracle PL / SQL
Oracle PL/SQL Tutorial
PostgreSQL
SQL / MySQL
MySQL Tutorial
VB.Net
VB.Net Tutorial
Flash / Flex / ActionScript
VBA / Excel / Access / Word
XML
XML Tutorial
Microsoft Office PowerPoint 2007 Tutorial
Microsoft Office Excel 2007 Tutorial
Microsoft Office Word 2007 Tutorial
Java Source Code / Java Documentation » 6.0 JDK Modules » j2me » com.sun.midp.jsr82emul 
Source Cross Referenced  Class Diagram Java Document (Java Doc) 


001:        /*
002:         *   
003:         *
004:         * Copyright  1990-2007 Sun Microsystems, Inc. All Rights Reserved.
005:         * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER
006:         * 
007:         * This program is free software; you can redistribute it and/or
008:         * modify it under the terms of the GNU General Public License version
009:         * 2 only, as published by the Free Software Foundation.
010:         * 
011:         * This program is distributed in the hope that it will be useful, but
012:         * WITHOUT ANY WARRANTY; without even the implied warranty of
013:         * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
014:         * General Public License version 2 for more details (a copy is
015:         * included at /legal/license.txt).
016:         * 
017:         * You should have received a copy of the GNU General Public License
018:         * version 2 along with this work; if not, write to the Free Software
019:         * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA
020:         * 02110-1301 USA
021:         * 
022:         * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa
023:         * Clara, CA 95054 or visit www.sun.com if you need additional
024:         * information or have any questions.
025:         */
026:        package com.sun.midp.jsr82emul;
027:
028:        import java.io.UnsupportedEncodingException;
029:        import java.io.IOException;
030:        import java.util.Vector;
031:
032:        import javax.bluetooth.DiscoveryListener;
033:        import javax.bluetooth.DiscoveryAgent;
034:
035:        import com.sun.kvem.jsr082.bluetooth.DiscoveryAgentImpl;
036:        import com.sun.midp.io.BluetoothUrl;
037:        import com.sun.midp.main.Configuration;
038:        import com.sun.midp.log.Logging;
039:        import com.sun.kvem.jsr082.bluetooth.BCC;
040:        import com.sun.midp.jsr082.BluetoothUtils;
041:
042:        /**
043:         * Emulates a Bluetooth device.
044:         */
045:        public class DeviceEmul extends EmulationClient implements  EmulUnit {
046:            /**
047:             * Represents and perfoms inquiry.
048:             * Constructing an instance starts inquiry in a new thread.
049:             */
050:            private class Inquiry implements  Runnable {
051:                /** Access code parameter for the inquiry. */
052:                int accessCode;
053:
054:                /** Indicates if this inquiry has been cancelled. */
055:                private boolean cancelled = false;
056:
057:                /** Inquiry thread. */
058:                private Thread thread;
059:
060:                /**
061:                 * Constructs an instance and starts corresponding inquiry thread.
062:                 * @param accessCode access code to be used within the inqiry
063:                 */
064:                Inquiry(int accessCode) {
065:                    this .accessCode = accessCode;
066:                    thread = new Thread(this );
067:                    thread.start();
068:                }
069:
070:                /** Cancells current inquiry. */
071:                synchronized void cancel() {
072:                    // not interrupting the corresponding thread to let it finish
073:                    // emulation server communications
074:                    cancelled = true;
075:                }
076:
077:                /**
078:                 * Implements <code>run()</code> of <code>Runnable</code> running
079:                 * the inquiry
080:                 */
081:                public void run() {
082:                    try {
083:                        InquiryResults inquiryResults;
084:
085:                        synchronized (serverTransaction) {
086:                            messenger.sendInt(toServer,
087:                                    Messenger.START_INQUIRY, accessCode);
088:
089:                            // let other threads work while the inquire is processed by
090:                            // emulation server
091:                            Thread.yield();
092:
093:                            messenger.receive(fromServer);
094:
095:                            if (messenger.getCode() != Messenger.INQUIRY_COMPLETED) {
096:                                throw new EmulationException();
097:                            }
098:
099:                            inquiryResults = new InquiryResults(messenger
100:                                    .getBytes());
101:                        }
102:
103:                        byte[][] addresses = inquiryResults.getAddresses();
104:                        int[] classes = inquiryResults.getClasses();
105:
106:                        for (int i = 0; i < addresses.length; i++) {
107:                            if (CheckCancelAndReportDiscovery(addresses[i],
108:                                    classes[i])) {
109:                                break;
110:                            }
111:                        }
112:
113:                        if (!cancelled) {
114:                            inquiryCompleted(true);
115:                        }
116:
117:                    } catch (Throwable e) {
118:                        inquiryCompleted(false);
119:                    }
120:
121:                }
122:
123:                /**
124:                 * Checks if inquiry cancelled and reports on device discovery to
125:                 * listener if it is not.
126:                 *
127:                 * @param btaddr BluetoothAddress of device discovered
128:                 * @param cod class of device discovered
129:                 * @return <code>true</code> if inquiry is cancelled,
130:                 *         <code>false</code> otherwise
131:                 */
132:                private synchronized boolean CheckCancelAndReportDiscovery(
133:                        byte[] btaddr, int cod) {
134:
135:                    if (!cancelled) {
136:                        deviceDiscovered(btaddr, cod);
137:                    }
138:                    return cancelled;
139:                }
140:            }
141:
142:            /** Initial access code. */
143:            private static int DEFAULT_AC = DiscoveryAgent.GIAC;
144:
145:            /** Keeps current inquiry if any. */
146:            private Inquiry curInquiry = null;
147:
148:            /** Bluetooth address. */
149:            byte[] address = null;
150:
151:            /** Device state i.e. discoverable mode and device class. */
152:            private DeviceState deviceState = null;
153:
154:            /** Lock for emulation server communications that require response. */
155:            private Object serverTransaction = new Object();
156:
157:            /** Device emulation for the local device. */
158:            private static DeviceEmul localDeviceEmul = null;
159:
160:            /**
161:             * Constructs an emulation instance and retrieves addres for it from
162:             *        emulation server.
163:             */
164:            public DeviceEmul() {
165:                try {
166:                    connect();
167:
168:                    messenger.sendBytes(toServer, Messenger.REGISTER_DEVICE,
169:                            getLocalIpBytes());
170:                    messenger.receive(fromServer);
171:
172:                    if (messenger.getCode() != Messenger.REGISTERED) {
173:                        throw new IOException(
174:                                "Error communicating emulation server");
175:                    }
176:
177:                    address = messenger.getBytes();
178:                    int cod = initDevice(address, DEFAULT_AC);
179:                    deviceState = new DeviceState(cod, DEFAULT_AC);
180:                    updateState();
181:
182:                    Log.log("DeviceEmul: my address is "
183:                            + BluetoothUtils.getAddressString(address));
184:                } catch (IOException e) {
185:                    throw new EmulationException(
186:                            "Error initializing local device emulation");
187:                }
188:            }
189:
190:            /** 
191:             * Initializes local device parameters in shared emulation storage.
192:             * @param addr Bluetoth address bytes retrieved form emulation server
193:             * @param ac initial access code
194:             * @return initial class of device with service classes that are possibly
195:             *         saved after previous usage of device with the same address
196:             */
197:            private native int initDevice(byte[] addr, int ac);
198:
199:            /**
200:             * Returns instance of this class for local device emulation.
201:             *
202:             * @return the device emulation object for the local device
203:             */
204:            public static synchronized DeviceEmul getLocalDeviceEmul() {
205:                if (localDeviceEmul == null) {
206:                    localDeviceEmul = new DeviceEmul();
207:                }
208:                return localDeviceEmul;
209:            }
210:
211:            /**
212:             * Retrieves IP address.
213:             * @return host computer IP address as byte array.
214:             */
215:            private byte[] getLocalIpBytes() {
216:                String ip = EmulationClient.getLocalIP();
217:                byte[] res = null;
218:
219:                if (ip != null && ip.length() > 0) {
220:                    int from = 0;
221:                    int to = 0;
222:                    byte[] parsed = new byte[4];
223:
224:                    try {
225:                        for (int i = 0; i < 4; i++) {
226:                            to = ip.indexOf('.', from);
227:                            if (to < 0) {
228:                                to = ip.length();
229:                            }
230:                            parsed[i] = (byte) Integer.parseInt(ip.substring(
231:                                    from, to));
232:                            from = to + 1;
233:                        }
234:
235:                        res = parsed;
236:                    } catch (NumberFormatException e) {
237:                        // res == null idenitifies retrieving failure
238:                    }
239:                }
240:
241:                if (res == null) {
242:                    res = new byte[] { 127, 0, 0, 1 };
243:                }
244:                return res;
245:            }
246:
247:            /**
248:             * Returns address of this device.
249:             * @return Bluetooth address
250:             */
251:            public byte[] getAddress() {
252:                return address;
253:            }
254:
255:            /**
256:             * Registers service at emulation server.
257:             * @param serviceData combined service connection info
258:             * @throws IOException if connection to emulation server failed.
259:             */
260:            void registerService(ServiceConnectionData serviceData)
261:                    throws IOException {
262:
263:                synchronized (serverTransaction) {
264:                    messenger
265:                            .sendBytes(
266:                                    toServer,
267:                                    Messenger.REGISTER_SERVICE,
268:                                    serviceData
269:                                            .toByteArray(ServiceConnectionData.SERVER_DATA));
270:                }
271:            }
272:
273:            /**
274:             * Unregisters service at emulation server.
275:             * @param serverSocketPort socket port desired service
276:             *        accepted connections at
277:             */
278:            void unregisterService(int serverSocketPort) {
279:                try {
280:                    messenger.sendInt(toServer, Messenger.UNREGISTER_SERVICE,
281:                            serverSocketPort);
282:                } catch (IOException e) {
283:                    if (Logging.TRACE_ENABLED) {
284:                        Logging.trace(e, "Unregistering service failed");
285:                    }
286:                }
287:            }
288:
289:            /** Sends device state update to emulation server. */
290:            private void updateState() {
291:                try {
292:                    messenger.sendInt(toServer, Messenger.UPDATE_DEVICE_STATE,
293:                            deviceState.toInt());
294:                } catch (IOException e) {
295:                    throw new EmulationException(e.getMessage());
296:                }
297:            }
298:
299:            /**
300:             * Starts inquiry.
301:             * @param accessCode access code of desired devices
302:             */
303:            private synchronized void startInquiry(int accessCode) {
304:                curInquiry = new Inquiry(accessCode);
305:            }
306:
307:            /**
308:             * Cancels current inquiry.
309:             */
310:            private synchronized void cancelInquiry() {
311:                if (curInquiry != null) {
312:                    curInquiry.cancel();
313:                }
314:            }
315:
316:            /** 
317:             * Notifies on device discovery. 
318:             * @param addr Bluetooth address of device discovered
319:             * @param cod class of device discovered
320:             */
321:            private native void deviceDiscovered(byte[] addr, int cod);
322:
323:            /** 
324:             * Notifies on inquiry completion.
325:             * @param success true if completed successfully, false otherwize
326:             */
327:            private native void inquiryCompleted(boolean success);
328:
329:            /** Request code for updating service classes. */
330:            static final int UPDATE_CLASS = 0;
331:            /** Request code for updating access code. */
332:            static final int UPDATE_ACCESS = 1;
333:            /** Request code for updating starting inquiry. */
334:            static final int START_INQUIRY = 2;
335:            /** Request code for cancelling inquiry. */
336:            static final int CANCEL_INQUIRY = 3;
337:            /** Request code for initing devie. */
338:            static final int INIT_DEVICE = 4;
339:
340:            /**
341:             * Processes the request.
342:             * @param request Packeted request
343:             */
344:            public void process(BytePack request) {
345:                switch (request.extract()) {
346:                case UPDATE_CLASS:
347:                    Log.log("Processing UPDATE_CLASS");
348:                    deviceState.setServiceClasses(request.extractInt());
349:                    updateState();
350:                    break;
351:                case UPDATE_ACCESS:
352:                    Log.log("Processing UPDATE_ACCESS");
353:                    deviceState.setDiscoverable(request.extractInt());
354:                    updateState();
355:                    break;
356:                case START_INQUIRY:
357:                    Log.log("Processing START_INQUIRY");
358:                    startInquiry(request.extractInt());
359:                    break;
360:                case CANCEL_INQUIRY:
361:                    Log.log("Processing CANCEL_INQUIRY");
362:                    cancelInquiry();
363:                    break;
364:                case INIT_DEVICE:
365:                    Log.log("Processing INIT_DEVICE");
366:                    // Nothing to do: the request has already caused 
367:                    // construction of all the objects required.
368:                    break;
369:                }
370:            }
371:
372:            /** 
373:             * Saves device information in persistent storage for future use. 
374:             */
375:            private native void finalize();
376:        }
377:
378:        /**
379:         * Utility class that allows packing inquiry results in bytes array.
380:         */
381:        class InquiryResults {
382:            /** Amount of devices discovered. */
383:            int count = 0;
384:
385:            /** Size of Bluetooth address byte representation. */
386:            private static final int ADDRESS_SIZE = Const.BTADDR_SIZE;
387:            /** Size of device class byte representation. */
388:            private static final int COD_SIZE = 3;
389:            /** Size of one result. */
390:            private static final int RESULT_SIZE = ADDRESS_SIZE + COD_SIZE;
391:
392:            /** Addresses of discovered devices if not <code>null</code>. */
393:            private byte[][] addresses;
394:            /** Classes of discovered devices if not <code>null</code>. */
395:            private int[] classes = null;
396:
397:            /** Inquiry results: Bluetooth address, device class pairs. */
398:            Vector results;
399:
400:            /** Constructs an instance for filling up. */
401:            InquiryResults() {
402:                results = new Vector();
403:            }
404:
405:            /**
406:             * Constructs an instance by byte representation and unpacks it to
407:             * normal addresses and device classes.
408:             *
409:             * @param data byte representation of inquiry results.
410:             */
411:            InquiryResults(byte[] data) {
412:                if (data == null || (data.length % RESULT_SIZE) != 0) {
413:                    throw new IllegalArgumentException();
414:                }
415:
416:                count = data.length / RESULT_SIZE;
417:                addresses = new byte[count][ADDRESS_SIZE];
418:                classes = new int[count];
419:
420:                for (int i = 0; i < count; i++) {
421:                    int j = i * RESULT_SIZE;
422:
423:                    classes[i] = (data[j++] & 0xff) | ((data[j++] & 0xff) << 8)
424:                            | ((data[j++] & 0xff) << 16);
425:
426:                    System.arraycopy(data, j, addresses[i], 0, ADDRESS_SIZE);
427:                }
428:            }
429:
430:            /**
431:             * Returns classes of discovered devices.
432:             * @return int array that contains classes of discovered devices
433:             */
434:            int[] getClasses() {
435:                if (classes == null) {
436:                    throw new IllegalArgumentException();
437:                }
438:                return classes;
439:            }
440:
441:            /**
442:             * Returns addresses of discovered devices
443:             * @return array of bluetooth addresses, byte representation.
444:             */
445:            byte[][] getAddresses() {
446:                if (addresses == null) {
447:                    throw new IllegalArgumentException();
448:                }
449:                return addresses;
450:            }
451:
452:            /**
453:             * Adds new device discovered to results.
454:             * @param btaddr Bluetooth address of device discovered
455:             * @param cod class of device discovered
456:             */
457:            void add(byte[] btaddr, int cod) {
458:                byte[] bytes = new byte[RESULT_SIZE];
459:
460:                bytes[0] = (byte) (cod & 0xff);
461:                bytes[1] = (byte) ((cod >> 8) & 0xff);
462:                bytes[2] = (byte) ((cod >> 16) & 0xff);
463:
464:                System.arraycopy(btaddr, 0, bytes, COD_SIZE, ADDRESS_SIZE);
465:
466:                results.addElement(bytes);
467:            }
468:
469:            /**
470:             * Packs results to byte representation.
471:             * @return byte array that represent current results
472:             */
473:            byte[] toByteArray() {
474:                count = results.size();
475:                byte[] data = new byte[count * RESULT_SIZE];
476:
477:                for (int i = 0; i < count; i++) {
478:                    System.arraycopy((byte[]) results.elementAt(i), 0, data, i
479:                            * RESULT_SIZE, RESULT_SIZE);
480:                }
481:
482:                return data;
483:            }
484:        }
485:
486:        /**
487:         * Utility class that allows packing device class and discoverable mode into
488:         * single integer.
489:         */
490:        class DeviceState {
491:            /** Packed information. */
492:            private int data = 0;
493:
494:            /** Mask for highlighting device class. */
495:            private static final int DEVICE_CLASS = 0x1ffc;
496:            /** Mask for highlighting device class. */
497:            private static final int SERV_CLASSES = 0xffe000;
498:            /** 
499:             * Mask for highlighting entire device class including device and 
500:             * service classes. 
501:             */
502:            private static final int COD = DEVICE_CLASS | SERV_CLASSES;
503:            /** Mask for highlighting a bit that shows device discoverable mode. */
504:            private static final int DISCOVERABLE = 0xff000000;
505:            /** LIAC bit. */
506:            private static final int LIAC = 0x01000000;
507:            /** GIAC bit. */
508:            private static final int GIAC = 0x02000000;
509:            /** Uniscoverable. */
510:            private static final int UNDISCOVERABLE = 0;
511:
512:            /**
513:             * Constructs an instance with given value.
514:             * @param cod value for class of device
515:             * @param mode value for discoverable mode
516:             */
517:            DeviceState(int cod, int mode) {
518:                data = cod;
519:                setDiscoverable(mode);
520:            }
521:
522:            /**
523:             * Constructs default state that is undiscoverable and has invalid
524:             * device class.
525:             */
526:            DeviceState() {
527:                this .data = UNDISCOVERABLE;
528:            }
529:
530:            /**
531:             * Retrieves integer representation.
532:             * @return integer representation
533:             */
534:            int toInt() {
535:                return data;
536:            }
537:
538:            /**
539:             * Retrieves entire class of device including device and service classes.
540:             * @return integer value that represents class of device.
541:             */
542:            int getCoD() {
543:                return data & COD;
544:            }
545:
546:            /**
547:             * Returns discoverable mode.
548:             * @return integer that represents discoverable mode.
549:             */
550:            int getDiscoverable() {
551:                switch (data & DISCOVERABLE) {
552:                case LIAC:
553:                    return DiscoveryAgent.LIAC;
554:                case GIAC:
555:                    return DiscoveryAgent.GIAC;
556:                default:
557:                    return DiscoveryAgent.NOT_DISCOVERABLE;
558:                }
559:            }
560:
561:            /**
562:             * Sets service classes of device.
563:             * @param classes new service classes value
564:             */
565:            void setServiceClasses(int classes) {
566:                data = data & (DISCOVERABLE | DEVICE_CLASS) | classes;
567:            }
568:
569:            /**
570:             * Sets discoverable mode to given one.
571:             * @param mode discoverable mode to set to
572:             * @return true if the discoverable mode is supported, otherwise - false
573:             */
574:            boolean setDiscoverable(int mode) {
575:                int bits = 0;
576:                boolean ret = true;
577:                switch (mode) {
578:                case DiscoveryAgent.LIAC:
579:                    bits = LIAC;
580:                    break;
581:                case DiscoveryAgent.GIAC:
582:                    bits = GIAC;
583:                    break;
584:                case DiscoveryAgent.NOT_DISCOVERABLE:
585:                    bits = UNDISCOVERABLE;
586:                    break;
587:                default:
588:                    ret = false;
589:                    break;
590:                }
591:                if (ret) {
592:                    data = bits | data & DEVICE_CLASS;
593:                }
594:                return ret;
595:            }
596:
597:            /**
598:             * Updates values from new integer representation.
599:             * @param data new integer representation
600:             */
601:            void update(int data) {
602:                this.data = data;
603:            }
604:        }
www.java2java.com | Contact Us
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.