24 #include "../../gsmstate.h" 26 #ifdef GSM_ENABLE_BLUETOOTHDEVICE 29 #include <CoreFoundation/CoreFoundation.h> 30 #include <IOBluetooth/Bluetooth.h> 31 #include <IOBluetooth/IOBluetoothUtilities.h> 32 #include <IOBluetooth/IOBluetoothUserLib.h> 36 IOBluetoothRFCOMMChannelRef rfcommChannel;
37 IOReturn ioReturnValue;
40 BluetoothDeviceAddress deviceAddress;
43 pthread_mutex_t mutexWait;
45 CFMutableArrayRef arrDataReceived;
53 static void thread_rfcommDataListener(IOBluetoothRFCOMMChannelRef rfcommChannel,
54 void* data, UInt16 length,
void* refCon)
56 threadContext *pContext = (threadContext *)refCon;
57 void *pBuffer = malloc(length);
58 dataBlock *pDataBlock = (dataBlock *)malloc(
sizeof(dataBlock));
60 memcpy(pBuffer, data, length);
62 pDataBlock->pData = pBuffer;
63 pDataBlock->nSize = length;
65 pthread_mutex_lock(&(pContext->mutexWait));
66 CFArrayAppendValue(pContext->arrDataReceived, pDataBlock);
67 pthread_mutex_unlock(&(pContext->mutexWait));
71 void thread_rfcommEventListener (IOBluetoothRFCOMMChannelRef rfcommChannel,
72 void *refCon, IOBluetoothRFCOMMChannelEvent *event)
74 if (event->eventType == kIOBluetoothRFCOMMNewDataEvent) {
75 thread_rfcommDataListener(rfcommChannel, event->u.newData.dataPtr, event->u.newData.dataSize , refCon);
82 static void *thread_main(
void *pArg)
84 threadContext* pContext = (threadContext *)pArg;
85 IOBluetoothDeviceRef device = IOBluetoothDeviceCreateWithAddress(&(pContext->deviceAddress));
86 IOBluetoothRFCOMMChannelRef rfcommChannel;
89 if (IOBluetoothDeviceOpenRFCOMMChannelSync(device, &rfcommChannel, pContext->nChannel,
90 thread_rfcommEventListener, pArg) != kIOReturnSuccess) {
94 if (IOBluetoothDeviceOpenRFCOMMChannel(device, pContext->nChannel,
95 &rfcommChannel) != kIOReturnSuccess) {
99 if (IOBluetoothRFCOMMChannelRegisterIncomingDataListener(rfcommChannel,
100 thread_rfcommDataListener, pArg) != kIOReturnSuccess) {
106 pContext->rfcommChannel = rfcommChannel;
108 pthread_mutex_unlock(&(pContext->mutexWait));
122 CFStringRef strDevice;
123 threadContext *pContext = (threadContext *)malloc(
sizeof(threadContext));
126 strDevice = CFStringCreateWithCString(kCFAllocatorDefault, device, kCFStringEncodingMacRomanLatin1);
127 IOBluetoothCFStringToDeviceAddress(strDevice, &pContext->deviceAddress);
128 CFRelease(strDevice);
130 pContext->arrDataReceived = CFArrayCreateMutable(kCFAllocatorDefault, 0, NULL);
131 pContext->rfcommChannel = 0;
132 pContext->nChannel = port;
134 pthread_mutex_init(&(pContext->mutexWait), NULL);
135 pthread_mutex_lock(&(pContext->mutexWait));
137 pthread_create(&(pContext->threadID), NULL, thread_main, pContext);
140 pthread_mutex_lock(&(pContext->mutexWait));
142 pthread_mutex_unlock(&(pContext->mutexWait));
144 if (pContext->rfcommChannel == 0) {
156 threadContext *pContext = (threadContext *)d->
Data;
157 IOBluetoothDeviceRef device;
161 if (pContext != NULL && pContext->rfcommChannel > 0) {
164 IOBluetoothRFCOMMChannelRegisterIncomingDataListener(pContext->rfcommChannel, NULL, NULL);
168 IOBluetoothRFCOMMChannelCloseChannel(pContext->rfcommChannel);
169 device = IOBluetoothRFCOMMChannelGetDevice(pContext->rfcommChannel);
170 IOBluetoothDeviceCloseConnection(device);
171 IOBluetoothObjectRelease(pContext->rfcommChannel);
172 IOBluetoothObjectRelease(device);
181 threadContext *pContext = (threadContext *)d->
Data;
184 if (IOBluetoothRFCOMMChannelWriteSync(pContext->rfcommChannel, (
void *)buf, nbytes) != kIOReturnSuccess)
187 if (IOBluetoothRFCOMMChannelWrite(pContext->rfcommChannel, (
void *)buf, nbytes,
TRUE) != kIOReturnSuccess)
197 threadContext *pContext = (threadContext *)d->
Data;
200 dataBlock* pDataBlock;
203 if (CFArrayGetCount(pContext->arrDataReceived) == 0)
206 while (CFArrayGetCount(pContext->arrDataReceived) != 0) {
207 pthread_mutex_lock(&(pContext->mutexWait));
208 pDataBlock = (dataBlock*)CFArrayGetValueAtIndex(pContext->arrDataReceived, 0);
209 pthread_mutex_unlock(&(pContext->mutexWait));
211 if (pDataBlock->nSize == size) {
213 memcpy(((
char *)buffer) + nOffset, pDataBlock->pData, size);
215 pthread_mutex_lock(&(pContext->mutexWait));
216 CFArrayRemoveValueAtIndex(pContext->arrDataReceived, 0);
217 pthread_mutex_unlock(&(pContext->mutexWait));
219 free(pDataBlock->pData);
220 pDataBlock->pData=NULL;
224 return nBytes + size;
225 }
else if (pDataBlock->nSize > size) {
227 memcpy(((
char *)buffer) + nOffset, pDataBlock->pData, size);
228 memmove(pDataBlock->pData, ((
char *)pDataBlock->pData) + size, pDataBlock->nSize - size);
229 pDataBlock->nSize -= size;
230 return nBytes + size;
233 memcpy(((
char *)buffer) + nOffset, pDataBlock->pData, pDataBlock->nSize);
235 size -= pDataBlock->nSize;
236 nOffset += pDataBlock->nSize;
237 nBytes += pDataBlock->nSize;
239 pthread_mutex_lock(&(pContext->mutexWait));
240 CFArrayRemoveValueAtIndex(pContext->arrDataReceived, 0);
241 pthread_mutex_unlock(&(pContext->mutexWait));
243 free(pDataBlock->pData);
244 pDataBlock->pData=NULL;
union GSM_Device::@0 Data
int bluetooth_write(GSM_StateMachine *s, const void *buf, size_t nbytes)
GSM_Error bluetooth_connect(GSM_StateMachine *s, int port, char *device)
GSM_Error bluetooth_close(GSM_StateMachine *s)
int bluetooth_read(GSM_StateMachine *s, void *buf, size_t nbytes)