Lines 31-36
Link Here
|
31 |
#include "shairport.h" |
31 |
#include "shairport.h" |
32 |
#include "hairtunes.h" |
32 |
#include "hairtunes.h" |
33 |
|
33 |
|
|
|
34 |
static struct printfPtr g_printf={NULL}; |
35 |
|
36 |
int xprintf(const char *format, ...) |
37 |
{ |
38 |
char dbg[2048]; |
39 |
va_list args; |
40 |
va_start(args, format); |
41 |
vsnprintf(dbg, sizeof(dbg), format, args); |
42 |
va_end(args); |
43 |
if(g_printf.extprintf) |
44 |
{ |
45 |
g_printf.extprintf(dbg, sizeof(dbg)); |
46 |
} |
47 |
else |
48 |
{ |
49 |
printf(dbg); |
50 |
} |
51 |
|
52 |
return 1; |
53 |
} |
54 |
|
34 |
#ifndef TRUE |
55 |
#ifndef TRUE |
35 |
#define TRUE (-1) |
56 |
#define TRUE (-1) |
36 |
#endif |
57 |
#endif |
Lines 98-103
Link Here
|
98 |
{ |
119 |
{ |
99 |
g_ao=*ao; |
120 |
g_ao=*ao; |
100 |
} |
121 |
} |
|
|
122 |
|
123 |
void shairport_set_printf(struct printfPtr *funcPtr) |
124 |
{ |
125 |
g_printf = *funcPtr; |
126 |
} |
101 |
#endif |
127 |
#endif |
102 |
|
128 |
|
103 |
#ifndef XBMC |
129 |
#ifndef XBMC |
Lines 106-112
Link Here
|
106 |
int shairport_main(int argc, char **argv) |
132 |
int shairport_main(int argc, char **argv) |
107 |
#endif |
133 |
#endif |
108 |
{ |
134 |
{ |
109 |
printf("initializing shairport\n"); |
135 |
xprintf("initializing shairport\n",NULL); |
110 |
char tHWID_Hex[HWID_SIZE * 2 + 1]; |
136 |
char tHWID_Hex[HWID_SIZE * 2 + 1]; |
111 |
char tKnownHwid[32]; |
137 |
char tKnownHwid[32]; |
112 |
|
138 |
|
Lines 185-206
Link Here
|
185 |
} |
211 |
} |
186 |
else if(!strcmp(arg, "-h") || !strcmp(arg, "--help")) |
212 |
else if(!strcmp(arg, "-h") || !strcmp(arg, "--help")) |
187 |
{ |
213 |
{ |
188 |
slog(LOG_INFO, "ShairPort version 0.05 C port - Airport Express emulator\n"); |
214 |
xprintf("ShairPort version 0.05 C port - Airport Express emulator\n"); |
189 |
slog(LOG_INFO, "Usage:\nshairport [OPTION...]\n\nOptions:\n"); |
215 |
xprintf("Usage:\nshairport [OPTION...]\n\nOptions:\n"); |
190 |
slog(LOG_INFO, " -a, --apname=AirPort Sets Airport name\n"); |
216 |
xprintf(" -a, --apname=AirPort Sets Airport name\n"); |
191 |
slog(LOG_INFO, " -p, --password=secret Sets Password (not working)\n"); |
217 |
xprintf(" -p, --password=secret Sets Password (not working)\n"); |
192 |
slog(LOG_INFO, " -o, --server_port=5000 Sets Port for Avahi/dns-sd\n"); |
218 |
xprintf(" -o, --server_port=5000 Sets Port for Avahi/dns-sd\n"); |
193 |
slog(LOG_INFO, " -b, --buffer=282 Sets Number of frames to buffer before beginning playback\n"); |
219 |
xprintf(" -b, --buffer=282 Sets Number of frames to buffer before beginning playback\n"); |
194 |
slog(LOG_INFO, " -d Daemon mode\n"); |
220 |
xprintf(" -d Daemon mode\n"); |
195 |
slog(LOG_INFO, " -q, --quiet Supresses all output.\n"); |
221 |
xprintf(" -q, --quiet Supresses all output.\n"); |
196 |
slog(LOG_INFO, " -v,-v2,-v3,-vv Various debugging levels\n"); |
222 |
xprintf(" -v,-v2,-v3,-vv Various debugging levels\n"); |
197 |
slog(LOG_INFO, "\n"); |
223 |
xprintf("\n"); |
198 |
return 0; |
224 |
return 0; |
199 |
} |
225 |
} |
200 |
} |
226 |
} |
201 |
|
227 |
|
202 |
if ( buffer_start_fill < 30 || buffer_start_fill > BUFFER_FRAMES ) { |
228 |
if ( buffer_start_fill < 30 || buffer_start_fill > BUFFER_FRAMES ) { |
203 |
fprintf(stderr, "buffer value must be > 30 and < %d\n", BUFFER_FRAMES); |
229 |
xprintf("buffer value must be > 30 and < %d\n", BUFFER_FRAMES); |
204 |
return(0); |
230 |
return(0); |
205 |
} |
231 |
} |
206 |
|
232 |
|
Lines 209-219
Link Here
|
209 |
int tPid = fork(); |
235 |
int tPid = fork(); |
210 |
if(tPid < 0) |
236 |
if(tPid < 0) |
211 |
{ |
237 |
{ |
212 |
exit(1); // Error on fork |
238 |
//exit(1); // Error on fork |
213 |
} |
239 |
} |
214 |
else if(tPid > 0) |
240 |
else if(tPid > 0) |
215 |
{ |
241 |
{ |
216 |
exit(0); |
242 |
//exit(0); |
217 |
} |
243 |
} |
218 |
else |
244 |
else |
219 |
{ |
245 |
{ |
Lines 254-263
Link Here
|
254 |
sscanf(tHWID_Hex, "%02X%02X%02X%02X%02X%02X", &tHWID[0], &tHWID[1], &tHWID[2], &tHWID[3], &tHWID[4], &tHWID[5]); |
280 |
sscanf(tHWID_Hex, "%02X%02X%02X%02X%02X%02X", &tHWID[0], &tHWID[1], &tHWID[2], &tHWID[3], &tHWID[4], &tHWID[5]); |
255 |
} |
281 |
} |
256 |
|
282 |
|
257 |
slog(LOG_INFO, "LogLevel: %d\n", kCurrentLogLevel); |
283 |
xprintf("LogLevel: %d\n", kCurrentLogLevel); |
258 |
slog(LOG_INFO, "AirName: %s\n", tServerName); |
284 |
xprintf("AirName: %s\n", tServerName); |
259 |
slog(LOG_INFO, "HWID: %.*s\n", HWID_SIZE, tHWID+1); |
285 |
xprintf("HWID: %.*s\n", HWID_SIZE, tHWID+1); |
260 |
slog(LOG_INFO, "HWID_Hex(%d): %s\n", strlen(tHWID_Hex), tHWID_Hex); |
286 |
xprintf("HWID_Hex(%d): %s\n", strlen(tHWID_Hex), tHWID_Hex); |
261 |
|
287 |
|
262 |
if(tSimLevel >= 1) |
288 |
if(tSimLevel >= 1) |
263 |
{ |
289 |
{ |
Lines 271-282
Link Here
|
271 |
#ifndef XBMC |
297 |
#ifndef XBMC |
272 |
startAvahi(tHWID_Hex, tServerName, tPort); |
298 |
startAvahi(tHWID_Hex, tServerName, tPort); |
273 |
#endif |
299 |
#endif |
274 |
slog(LOG_DEBUG_V, "Starting connection server: specified server port: %d\n", tPort); |
300 |
xprintf("Starting connection server: specified server port: %d\n", tPort); |
275 |
tServerSock = setupListenServer(&tAddrInfo, tPort); |
301 |
tServerSock = setupListenServer(&tAddrInfo, tPort); |
276 |
if(tServerSock < 0) |
302 |
if(tServerSock < 0) |
277 |
{ |
303 |
{ |
278 |
freeaddrinfo(tAddrInfo); |
304 |
freeaddrinfo(tAddrInfo); |
279 |
slog(LOG_INFO, "Error setting up server socket on port %d, try specifying a different port\n", tPort); |
305 |
xprintf("Error setting up server socket on port %d, try specifying a different port\n", tPort); |
280 |
return 0; |
306 |
return 0; |
281 |
} |
307 |
} |
282 |
|
308 |
|
Lines 303-309
Link Here
|
303 |
|
329 |
|
304 |
int readsock; |
330 |
int readsock; |
305 |
|
331 |
|
306 |
slog(LOG_DEBUG_V, "Waiting for clients to connect\n"); |
332 |
xprintf("Waiting for clients to connect\n"); |
307 |
|
333 |
|
308 |
while(m_running) |
334 |
while(m_running) |
309 |
{ |
335 |
{ |
Lines 335-341
Link Here
|
335 |
{ |
361 |
{ |
336 |
freeaddrinfo(tAddrInfo); |
362 |
freeaddrinfo(tAddrInfo); |
337 |
tAddrInfo = NULL; |
363 |
tAddrInfo = NULL; |
338 |
slog(LOG_DEBUG, "...Accepted Client Connection..\n"); |
364 |
xprintf("...Accepted Client Connection..\n"); |
339 |
close(tServerSock); |
365 |
close(tServerSock); |
340 |
handleClient(tClientSock, tPassword, tHWID); |
366 |
handleClient(tClientSock, tPassword, tHWID); |
341 |
//close(tClientSock); |
367 |
//close(tClientSock); |
Lines 343-353
Link Here
|
343 |
} |
369 |
} |
344 |
else |
370 |
else |
345 |
{ |
371 |
{ |
346 |
slog(LOG_DEBUG_VV, "Child now busy handling new client\n"); |
372 |
xprintf("Child now busy handling new client\n"); |
347 |
close(tClientSock); |
373 |
close(tClientSock); |
348 |
} |
374 |
} |
349 |
#else |
375 |
#else |
350 |
slog(LOG_DEBUG, "...Accepted Client Connection..\n"); |
376 |
xprintf("...Accepted Client Connection..\n"); |
351 |
handleClient(tClientSock, tPassword, tHWID); |
377 |
handleClient(tClientSock, tPassword, tHWID); |
352 |
#endif |
378 |
#endif |
353 |
} |
379 |
} |
Lines 357-363
Link Here
|
357 |
} |
383 |
} |
358 |
} |
384 |
} |
359 |
|
385 |
|
360 |
slog(LOG_DEBUG_VV, "Finished\n"); |
386 |
xprintf("Finished\n"); |
361 |
if(tAddrInfo != NULL) |
387 |
if(tAddrInfo != NULL) |
362 |
{ |
388 |
{ |
363 |
freeaddrinfo(tAddrInfo); |
389 |
freeaddrinfo(tAddrInfo); |
Lines 416-422
Link Here
|
416 |
|
442 |
|
417 |
void handleClient(int pSock, char *pPassword, char *pHWADDR) |
443 |
void handleClient(int pSock, char *pPassword, char *pHWADDR) |
418 |
{ |
444 |
{ |
419 |
slog(LOG_DEBUG_VV, "In Handle Client\n"); |
445 |
xprintf("In Handle Client\n"); |
420 |
fflush(stdout); |
446 |
fflush(stdout); |
421 |
|
447 |
|
422 |
socklen_t len; |
448 |
socklen_t len; |
Lines 435-441
Link Here
|
435 |
|
461 |
|
436 |
// deal with both IPv4 and IPv6: |
462 |
// deal with both IPv4 and IPv6: |
437 |
if (addr.ss_family == AF_INET) { |
463 |
if (addr.ss_family == AF_INET) { |
438 |
slog(LOG_DEBUG_V, "Constructing ipv4 address\n"); |
464 |
xprintf("Constructing ipv4 address\n"); |
439 |
struct sockaddr_in *s = (struct sockaddr_in *)&addr; |
465 |
struct sockaddr_in *s = (struct sockaddr_in *)&addr; |
440 |
port = ntohs(s->sin_port); |
466 |
port = ntohs(s->sin_port); |
441 |
inet_ntop(AF_INET, &s->sin_addr, ipstr, sizeof ipstr); |
467 |
inet_ntop(AF_INET, &s->sin_addr, ipstr, sizeof ipstr); |
Lines 455-474
Link Here
|
455 |
if(memcmp(&addr.bin[0], "\x00\x00\x00\x00" "\x00\x00\x00\x00" "\x00\x00\xff\xff", 12) == 0) |
481 |
if(memcmp(&addr.bin[0], "\x00\x00\x00\x00" "\x00\x00\x00\x00" "\x00\x00\xff\xff", 12) == 0) |
456 |
{ |
482 |
{ |
457 |
// its ipv4... |
483 |
// its ipv4... |
458 |
slog(LOG_DEBUG_V, "Constructing ipv4 from ipv6 address\n"); |
484 |
xprintf("Constructing ipv4 from ipv6 address\n"); |
459 |
memcpy(ipbin, &addr.bin[12], 4); |
485 |
memcpy(ipbin, &addr.bin[12], 4); |
460 |
ipbinlen = 4; |
486 |
ipbinlen = 4; |
461 |
} |
487 |
} |
462 |
else |
488 |
else |
463 |
{ |
489 |
{ |
464 |
slog(LOG_DEBUG_V, "Constructing ipv6 address\n"); |
490 |
xprintf("Constructing ipv6 address\n"); |
465 |
memcpy(ipbin, &s->sin6_addr, 16); |
491 |
memcpy(ipbin, &s->sin6_addr, 16); |
466 |
ipbinlen = 16; |
492 |
ipbinlen = 16; |
467 |
} |
493 |
} |
468 |
} |
494 |
} |
469 |
|
495 |
|
470 |
slog(LOG_DEBUG_V, "Peer IP address: %s\n", ipstr); |
496 |
xprintf("Peer IP address: %s\n", ipstr); |
471 |
slog(LOG_DEBUG_V, "Peer port : %d\n", port); |
497 |
xprintf("Peer port : %d\n", port); |
472 |
|
498 |
|
473 |
int tMoreDataNeeded = 1; |
499 |
int tMoreDataNeeded = 1; |
474 |
struct keyring tKeys; |
500 |
struct keyring tKeys; |
Lines 489-504
Link Here
|
489 |
tError = readDataFromClient(pSock, &(tConn.recv)); |
515 |
tError = readDataFromClient(pSock, &(tConn.recv)); |
490 |
if(!tError && strlen(tConn.recv.data) > 0) |
516 |
if(!tError && strlen(tConn.recv.data) > 0) |
491 |
{ |
517 |
{ |
492 |
slog(LOG_DEBUG_VV, "Finished Reading some data from client\n"); |
518 |
xprintf("Finished Reading some data from client\n"); |
493 |
// parse client request |
519 |
// parse client request |
494 |
tMoreDataNeeded = parseMessage(&tConn, ipbin, ipbinlen, pHWADDR); |
520 |
tMoreDataNeeded = parseMessage(&tConn, ipbin, ipbinlen, pHWADDR); |
495 |
if(1 == tMoreDataNeeded) |
521 |
if(1 == tMoreDataNeeded) |
496 |
{ |
522 |
{ |
497 |
slog(LOG_DEBUG_VV, "\n\nNeed to read more data\n"); |
523 |
xprintf("\n\nNeed to read more data\n"); |
498 |
} |
524 |
} |
499 |
else if(-1 == tMoreDataNeeded) // Forked process down below ended. |
525 |
else if(-1 == tMoreDataNeeded) // Forked process down below ended. |
500 |
{ |
526 |
{ |
501 |
slog(LOG_DEBUG_V, "Forked Process ended...cleaning up\n"); |
527 |
xprintf("Forked Process ended...cleaning up\n"); |
502 |
cleanup(&tConn); |
528 |
cleanup(&tConn); |
503 |
// pSock was already closed |
529 |
// pSock was already closed |
504 |
return; |
530 |
return; |
Lines 507-519
Link Here
|
507 |
} |
533 |
} |
508 |
else |
534 |
else |
509 |
{ |
535 |
{ |
510 |
slog(LOG_DEBUG, "Error reading from socket, closing client\n"); |
536 |
xprintf("Error reading from socket, closing client\n"); |
511 |
// Error reading data....quit. |
537 |
// Error reading data....quit. |
512 |
cleanup(&tConn); |
538 |
cleanup(&tConn); |
513 |
return; |
539 |
return; |
514 |
} |
540 |
} |
515 |
} |
541 |
} |
516 |
slog(LOG_DEBUG_VV, "Writing: %d chars to socket\n", tConn.resp.current); |
542 |
xprintf("Writing: %d chars to socket\n", tConn.resp.current); |
517 |
//tConn->resp.data[tConn->resp.current-1] = '\0'; |
543 |
//tConn->resp.data[tConn->resp.current-1] = '\0'; |
518 |
writeDataToClient(pSock, &(tConn.resp)); |
544 |
writeDataToClient(pSock, &(tConn.resp)); |
519 |
// Finished reading one message... |
545 |
// Finished reading one message... |
Lines 526-534
Link Here
|
526 |
|
552 |
|
527 |
void writeDataToClient(int pSock, struct shairbuffer *pResponse) |
553 |
void writeDataToClient(int pSock, struct shairbuffer *pResponse) |
528 |
{ |
554 |
{ |
529 |
slog(LOG_DEBUG_VV, "\n----Beg Send Response Header----\n%.*s\n", pResponse->current, pResponse->data); |
555 |
xprintf("\n----Beg Send Response Header----\n%.*s\n", pResponse->current, pResponse->data); |
530 |
send(pSock, pResponse->data, pResponse->current,0); |
556 |
send(pSock, pResponse->data, pResponse->current,0); |
531 |
slog(LOG_DEBUG_VV, "----Send Response Header----\n"); |
557 |
xprintf("----Send Response Header----\n"); |
532 |
} |
558 |
} |
533 |
|
559 |
|
534 |
int readDataFromClient(int pSock, struct shairbuffer *pClientBuffer) |
560 |
int readDataFromClient(int pSock, struct shairbuffer *pClientBuffer) |
Lines 541-547
Link Here
|
541 |
while(tRetval > 0 && tEnd < 0) |
567 |
while(tRetval > 0 && tEnd < 0) |
542 |
{ |
568 |
{ |
543 |
// Read from socket until \n\n, \r\n\r\n, or \r\r is found |
569 |
// Read from socket until \n\n, \r\n\r\n, or \r\r is found |
544 |
slog(LOG_DEBUG_V, "Waiting To Read...\n"); |
570 |
xprintf("Waiting To Read...\n"); |
545 |
fflush(stdout); |
571 |
fflush(stdout); |
546 |
tRetval = read(pSock, tReadBuf, MAX_SIZE); |
572 |
tRetval = read(pSock, tReadBuf, MAX_SIZE); |
547 |
// if new buffer contains the end of request string, only copy partial buffer? |
573 |
// if new buffer contains the end of request string, only copy partial buffer? |
Lines 552-591
Link Here
|
552 |
{ |
578 |
{ |
553 |
pClientBuffer->marker = tEnd+1; // Marks start of content |
579 |
pClientBuffer->marker = tEnd+1; // Marks start of content |
554 |
} |
580 |
} |
555 |
slog(SOCKET_LOG_LEVEL, "Found end of http request at: %d\n", tEnd); |
581 |
xprintf("Found end of http request at: %d\n", tEnd); |
556 |
fflush(stdout); |
582 |
fflush(stdout); |
557 |
} |
583 |
} |
558 |
else |
584 |
else |
559 |
{ |
585 |
{ |
560 |
tEnd = MAX_SIZE; |
586 |
tEnd = MAX_SIZE; |
561 |
slog(SOCKET_LOG_LEVEL, "Read %d of data so far\n%s\n", tRetval, tReadBuf); |
587 |
xprintf("Read %d of data so far\n%s\n", tRetval, tReadBuf); |
562 |
fflush(stdout); |
588 |
fflush(stdout); |
563 |
} |
589 |
} |
564 |
if(tRetval > 0) |
590 |
if(tRetval > 0) |
565 |
{ |
591 |
{ |
566 |
// Copy read data into tReceive; |
592 |
// Copy read data into tReceive; |
567 |
slog(SOCKET_LOG_LEVEL, "Read %d data, using %d of it\n", tRetval, tEnd); |
593 |
xprintf("Read %d data, using %d of it\n", tRetval, tEnd); |
568 |
addNToShairBuffer(pClientBuffer, tReadBuf, tRetval); |
594 |
addNToShairBuffer(pClientBuffer, tReadBuf, tRetval); |
569 |
slog(LOG_DEBUG_VV, "Finished copying data\n"); |
595 |
xprintf("Finished copying data\n"); |
570 |
} |
596 |
} |
571 |
else |
597 |
else |
572 |
{ |
598 |
{ |
573 |
slog(LOG_DEBUG, "Error reading data from socket, got: %d bytes", tRetval); |
599 |
xprintf("Error reading data from socket, got: %d bytes", tRetval); |
574 |
return tRetval; |
600 |
return tRetval; |
575 |
} |
601 |
} |
576 |
} |
602 |
} |
577 |
if(tEnd + 1 != tRetval) |
603 |
if(tEnd + 1 != tRetval) |
578 |
{ |
604 |
{ |
579 |
slog(SOCKET_LOG_LEVEL, "Read more data after end of http request. %d instead of %d\n", tRetval, tEnd+1); |
605 |
xprintf("Read more data after end of http request. %d instead of %d\n", tRetval, tEnd+1); |
580 |
} |
606 |
} |
581 |
slog(SOCKET_LOG_LEVEL, "Finished Reading Data:\n%s\nEndOfData\n", pClientBuffer->data); |
607 |
xprintf("Finished Reading Data:\n%s\nEndOfData\n", pClientBuffer->data); |
582 |
fflush(stdout); |
608 |
fflush(stdout); |
583 |
return 0; |
609 |
return 0; |
584 |
} |
610 |
} |
585 |
|
611 |
|
586 |
char *getFromBuffer(char *pBufferPtr, const char *pField, int pLenAfterField, int *pReturnSize, char *pDelims) |
612 |
char *getFromBuffer(char *pBufferPtr, const char *pField, int pLenAfterField, int *pReturnSize, char *pDelims) |
587 |
{ |
613 |
{ |
588 |
slog(LOG_DEBUG_V, "GettingFromBuffer: %s\n", pField); |
614 |
xprintf("GettingFromBuffer: %s\n", pField); |
589 |
char* tFound = strstr(pBufferPtr, pField); |
615 |
char* tFound = strstr(pBufferPtr, pField); |
590 |
int tSize = 0; |
616 |
int tSize = 0; |
591 |
if(tFound != NULL) |
617 |
if(tFound != NULL) |
Lines 606-612
Link Here
|
606 |
} |
632 |
} |
607 |
|
633 |
|
608 |
tSize = (int) (tShortest - tFound); |
634 |
tSize = (int) (tShortest - tFound); |
609 |
slog(LOG_DEBUG_VV, "Found %.*s length: %d\n", tSize, tFound, tSize); |
635 |
xprintf("Found %.*s length: %d\n", tSize, tFound, tSize); |
610 |
if(pReturnSize != NULL) |
636 |
if(pReturnSize != NULL) |
611 |
{ |
637 |
{ |
612 |
*pReturnSize = tSize; |
638 |
*pReturnSize = tSize; |
Lines 614-620
Link Here
|
614 |
} |
640 |
} |
615 |
else |
641 |
else |
616 |
{ |
642 |
{ |
617 |
slog(LOG_DEBUG_V, "Not Found\n"); |
643 |
xprintf("Not Found\n"); |
618 |
} |
644 |
} |
619 |
return tFound; |
645 |
return tFound; |
620 |
} |
646 |
} |
Lines 648-657
Link Here
|
648 |
{ |
674 |
{ |
649 |
char tTrim[tFoundSize + 2]; |
675 |
char tTrim[tFoundSize + 2]; |
650 |
getTrimmed(tFound, tFoundSize, TRUE, TRUE, tTrim); |
676 |
getTrimmed(tFound, tFoundSize, TRUE, TRUE, tTrim); |
651 |
slog(LOG_DEBUG_VV, "HeaderChallenge: [%s] len: %d sizeFound: %d\n", tTrim, strlen(tTrim), tFoundSize); |
677 |
xprintf("HeaderChallenge: [%s] len: %d sizeFound: %d\n", tTrim, strlen(tTrim), tFoundSize); |
652 |
int tChallengeDecodeSize = 16; |
678 |
int tChallengeDecodeSize = 16; |
653 |
char *tChallenge = decode_base64((unsigned char *)tTrim, tFoundSize, &tChallengeDecodeSize); |
679 |
char *tChallenge = decode_base64((unsigned char *)tTrim, tFoundSize, &tChallengeDecodeSize); |
654 |
slog(LOG_DEBUG_VV, "Challenge Decode size: %d expected 16\n", tChallengeDecodeSize); |
680 |
xprintf("Challenge Decode size: %d expected 16\n", tChallengeDecodeSize); |
655 |
|
681 |
|
656 |
int tCurSize = 0; |
682 |
int tCurSize = 0; |
657 |
unsigned char tChalResp[38]; |
683 |
unsigned char tChalResp[38]; |
Lines 673-679
Link Here
|
673 |
} |
699 |
} |
674 |
|
700 |
|
675 |
char *tTmp = encode_base64((unsigned char *)tChalResp, tCurSize); |
701 |
char *tTmp = encode_base64((unsigned char *)tChalResp, tCurSize); |
676 |
slog(LOG_DEBUG_VV, "Full sig: %s\n", tTmp); |
702 |
xprintf("Full sig: %s\n", tTmp); |
677 |
free(tTmp); |
703 |
free(tTmp); |
678 |
|
704 |
|
679 |
// RSA Encrypt |
705 |
// RSA Encrypt |
Lines 722-731
Link Here
|
722 |
{ |
748 |
{ |
723 |
if(isLogEnabledFor(HEADER_LOG_LEVEL)) |
749 |
if(isLogEnabledFor(HEADER_LOG_LEVEL)) |
724 |
{ |
750 |
{ |
725 |
slog(HEADER_LOG_LEVEL, "Content-Length: %s value -> %d\n", tContent, tContentSize); |
751 |
xprintf("Content-Length: %s value -> %d\n", tContent, tContentSize); |
726 |
if(pConn->recv.marker != 0) |
752 |
if(pConn->recv.marker != 0) |
727 |
{ |
753 |
{ |
728 |
slog(HEADER_LOG_LEVEL, "ContentPtr has %d, but needs %d\n", |
754 |
xprintf("ContentPtr has %d, but needs %d\n", |
729 |
strlen(pConn->recv.data+pConn->recv.marker), tContentSize); |
755 |
strlen(pConn->recv.data+pConn->recv.marker), tContentSize); |
730 |
} |
756 |
} |
731 |
} |
757 |
} |
Lines 735-741
Link Here
|
735 |
} |
761 |
} |
736 |
else |
762 |
else |
737 |
{ |
763 |
{ |
738 |
slog(LOG_DEBUG_VV, "No content, header only\n"); |
764 |
xprintf("No content, header only\n"); |
739 |
} |
765 |
} |
740 |
|
766 |
|
741 |
// "Creates" a new Response Header for our response message |
767 |
// "Creates" a new Response Header for our response message |
Lines 748-754
Link Here
|
748 |
{ |
774 |
{ |
749 |
tLen = 20; |
775 |
tLen = 20; |
750 |
} |
776 |
} |
751 |
slog(LOG_INFO, "********** RECV %.*s **********\n", tLen, pConn->recv.data); |
777 |
xprintf("********** RECV %.*s **********\n", tLen, pConn->recv.data); |
752 |
} |
778 |
} |
753 |
|
779 |
|
754 |
if(pConn->password != NULL) |
780 |
if(pConn->password != NULL) |
Lines 758-764
Link Here
|
758 |
|
784 |
|
759 |
if(buildAppleResponse(pConn, pIpBin, pIpBinLen, pHWID)) // need to free sig |
785 |
if(buildAppleResponse(pConn, pIpBin, pIpBinLen, pHWID)) // need to free sig |
760 |
{ |
786 |
{ |
761 |
slog(LOG_DEBUG_V, "Added AppleResponse to Apple-Challenge request\n"); |
787 |
xprintf("Added AppleResponse to Apple-Challenge request\n"); |
762 |
} |
788 |
} |
763 |
|
789 |
|
764 |
// Find option, then based on option, do different actions. |
790 |
// Find option, then based on option, do different actions. |
Lines 778-791
Link Here
|
778 |
int tKeySize = 0; |
804 |
int tKeySize = 0; |
779 |
char tEncodedAesIV[tSize + 2]; |
805 |
char tEncodedAesIV[tSize + 2]; |
780 |
getTrimmed(tHeaderVal, tSize, TRUE, TRUE, tEncodedAesIV); |
806 |
getTrimmed(tHeaderVal, tSize, TRUE, TRUE, tEncodedAesIV); |
781 |
slog(LOG_DEBUG_VV, "AESIV: [%.*s] Size: %d Strlen: %d\n", tSize, tEncodedAesIV, tSize, strlen(tEncodedAesIV)); |
807 |
xprintf("AESIV: [%.*s] Size: %d Strlen: %d\n", tSize, tEncodedAesIV, tSize, strlen(tEncodedAesIV)); |
782 |
char *tDecodedIV = decode_base64((unsigned char*) tEncodedAesIV, tSize, &tSize); |
808 |
char *tDecodedIV = decode_base64((unsigned char*) tEncodedAesIV, tSize, &tSize); |
783 |
|
809 |
|
784 |
// grab the key, copy it out of the receive buffer |
810 |
// grab the key, copy it out of the receive buffer |
785 |
tHeaderVal = getFromContent(tContent, "a=rsaaeskey", &tKeySize); |
811 |
tHeaderVal = getFromContent(tContent, "a=rsaaeskey", &tKeySize); |
786 |
char tEncodedAesKey[tKeySize + 2]; // +1 for nl, +1 for \0 |
812 |
char tEncodedAesKey[tKeySize + 2]; // +1 for nl, +1 for \0 |
787 |
getTrimmed(tHeaderVal, tKeySize, TRUE, TRUE, tEncodedAesKey); |
813 |
getTrimmed(tHeaderVal, tKeySize, TRUE, TRUE, tEncodedAesKey); |
788 |
slog(LOG_DEBUG_VV, "AES KEY: [%s] Size: %d Strlen: %d\n", tEncodedAesKey, tKeySize, strlen(tEncodedAesKey)); |
814 |
xprintf("AES KEY: [%s] Size: %d Strlen: %d\n", tEncodedAesKey, tKeySize, strlen(tEncodedAesKey)); |
789 |
// remove base64 coding from key |
815 |
// remove base64 coding from key |
790 |
char *tDecodedAesKey = decode_base64((unsigned char*) tEncodedAesKey, |
816 |
char *tDecodedAesKey = decode_base64((unsigned char*) tEncodedAesKey, |
791 |
tKeySize, &tKeySize); // Need to free DecodedAesKey |
817 |
tKeySize, &tKeySize); // Need to free DecodedAesKey |
Lines 794-800
Link Here
|
794 |
int tFmtpSize = 0; |
820 |
int tFmtpSize = 0; |
795 |
char *tFmtp = getFromContent(tContent, "a=fmtp", &tFmtpSize); // Don't need to free |
821 |
char *tFmtp = getFromContent(tContent, "a=fmtp", &tFmtpSize); // Don't need to free |
796 |
tFmtp = getTrimmedMalloc(tFmtp, tFmtpSize, TRUE, FALSE); // will need to free |
822 |
tFmtp = getTrimmedMalloc(tFmtp, tFmtpSize, TRUE, FALSE); // will need to free |
797 |
slog(LOG_DEBUG_VV, "Format: %s\n", tFmtp); |
823 |
xprintf("Format: %s\n", tFmtp); |
798 |
|
824 |
|
799 |
RSA *rsa = loadKey(); |
825 |
RSA *rsa = loadKey(); |
800 |
// Decrypt the binary aes key |
826 |
// Decrypt the binary aes key |
Lines 803-813
Link Here
|
803 |
if(RSA_private_decrypt(tKeySize, (unsigned char *)tDecodedAesKey, |
829 |
if(RSA_private_decrypt(tKeySize, (unsigned char *)tDecodedAesKey, |
804 |
(unsigned char*) tDecryptedKey, rsa, RSA_PKCS1_OAEP_PADDING) >= 0) |
830 |
(unsigned char*) tDecryptedKey, rsa, RSA_PKCS1_OAEP_PADDING) >= 0) |
805 |
{ |
831 |
{ |
806 |
slog(LOG_DEBUG, "Decrypted AES key from RSA Successfully\n"); |
832 |
xprintf("Decrypted AES key from RSA Successfully\n"); |
807 |
} |
833 |
} |
808 |
else |
834 |
else |
809 |
{ |
835 |
{ |
810 |
slog(LOG_INFO, "Error Decrypting AES key from RSA\n"); |
836 |
xprintf("Error Decrypting AES key from RSA\n"); |
811 |
} |
837 |
} |
812 |
free(tDecodedAesKey); |
838 |
free(tDecodedAesKey); |
813 |
RSA_free(rsa); |
839 |
RSA_free(rsa); |
Lines 823-835
Link Here
|
823 |
// struct comms *tComms = pConn->hairtunes; |
849 |
// struct comms *tComms = pConn->hairtunes; |
824 |
// if (! (pipe(tComms->in) == 0 && pipe(tComms->out) == 0)) |
850 |
// if (! (pipe(tComms->in) == 0 && pipe(tComms->out) == 0)) |
825 |
// { |
851 |
// { |
826 |
// slog(LOG_INFO, "Error setting up hairtunes communications...some things probably wont work very well.\n"); |
852 |
// xprintf("Error setting up hairtunes communications...some things probably wont work very well.\n"); |
827 |
// } |
853 |
// } |
828 |
|
854 |
|
829 |
// Setup fork |
855 |
// Setup fork |
830 |
char tPort[8] = "6000"; // get this from dup()'d stdout of child pid |
856 |
char tPort[8] = "6000"; // get this from dup()'d stdout of child pid |
831 |
|
857 |
|
832 |
printf("******** SETUP!!!!!\n"); |
858 |
xprintf("******** SETUP!!!!!\n",NULL); |
833 |
#ifndef XBMC |
859 |
#ifndef XBMC |
834 |
int tPid = fork(); |
860 |
int tPid = fork(); |
835 |
if(tPid == 0) |
861 |
if(tPid == 0) |
Lines 845-855
Link Here
|
845 |
tFound = getFromSetup(pConn->recv.data, "timing_port", &tSize); |
871 |
tFound = getFromSetup(pConn->recv.data, "timing_port", &tSize); |
846 |
getTrimmed(tFound, tSize, 1, 0, tTPortStr); |
872 |
getTrimmed(tFound, tSize, 1, 0, tTPortStr); |
847 |
|
873 |
|
848 |
slog(LOG_DEBUG_VV, "converting %s and %s from str->int\n", tCPortStr, tTPortStr); |
874 |
xprintf("converting %s and %s from str->int\n", tCPortStr, tTPortStr); |
849 |
int tControlport = atoi(tCPortStr); |
875 |
int tControlport = atoi(tCPortStr); |
850 |
int tTimingport = atoi(tTPortStr); |
876 |
int tTimingport = atoi(tTPortStr); |
851 |
|
877 |
|
852 |
slog(LOG_DEBUG_V, "Got %d for CPort and %d for TPort\n", tControlport, tTimingport); |
878 |
xprintf("Got %d for CPort and %d for TPort\n", tControlport, tTimingport); |
853 |
char *tRtp = NULL; |
879 |
char *tRtp = NULL; |
854 |
char *tPipe = NULL; |
880 |
char *tPipe = NULL; |
855 |
char *tAoDriver = NULL; |
881 |
char *tAoDriver = NULL; |
Lines 884-890
Link Here
|
884 |
tDataport, tRtp, tPipe, tAoDriver, tAoDeviceName, tAoDeviceId); |
910 |
tDataport, tRtp, tPipe, tAoDriver, tAoDeviceName, tAoDeviceId); |
885 |
#ifndef XBMC |
911 |
#ifndef XBMC |
886 |
// Quit when finished. |
912 |
// Quit when finished. |
887 |
slog(LOG_DEBUG, "Returned from hairtunes init....returning -1, should close out this whole side of the fork\n"); |
913 |
xprintf("Returned from hairtunes init....returning -1, should close out this whole side of the fork\n"); |
888 |
return -1; |
914 |
return -1; |
889 |
} |
915 |
} |
890 |
else if(tPid >0) |
916 |
else if(tPid >0) |
Lines 897-903
Link Here
|
897 |
int tRead = read(tComms->out[0], tFromHairtunes, 80); |
923 |
int tRead = read(tComms->out[0], tFromHairtunes, 80); |
898 |
if(tRead <= 0) |
924 |
if(tRead <= 0) |
899 |
{ |
925 |
{ |
900 |
slog(LOG_INFO, "Error reading port from hairtunes function, assuming default port: %d\n", tPort); |
926 |
xprintf("Error reading port from hairtunes function, assuming default port: %d\n", tPort); |
901 |
} |
927 |
} |
902 |
else |
928 |
else |
903 |
{ |
929 |
{ |
Lines 909-915
Link Here
|
909 |
} |
935 |
} |
910 |
else |
936 |
else |
911 |
{ |
937 |
{ |
912 |
slog(LOG_INFO, "Read %d bytes, Error translating %s into a port\n", tRead, tFromHairtunes); |
938 |
xprintf("Read %d bytes, Error translating %s into a port\n", tRead, tFromHairtunes); |
913 |
} |
939 |
} |
914 |
} |
940 |
} |
915 |
|
941 |
|
Lines 930-936
Link Here
|
930 |
} |
956 |
} |
931 |
else |
957 |
else |
932 |
{ |
958 |
{ |
933 |
slog(LOG_INFO, "Error forking process....dere' be errors round here.\n"); |
959 |
xprintf("Error forking process....dere' be errors round here.\n"); |
934 |
return -1; |
960 |
return -1; |
935 |
} |
961 |
} |
936 |
#endif |
962 |
#endif |
Lines 942-948
Link Here
|
942 |
propogateCSeq(pConn); |
968 |
propogateCSeq(pConn); |
943 |
#ifndef XBMC |
969 |
#ifndef XBMC |
944 |
close(pConn->hairtunes->in[1]); |
970 |
close(pConn->hairtunes->in[1]); |
945 |
slog(LOG_DEBUG, "Tearing down connection, closing pipes\n"); |
971 |
xprintf("Tearing down connection, closing pipes\n"); |
946 |
#else |
972 |
#else |
947 |
hairtunes_cleanup(); |
973 |
hairtunes_cleanup(); |
948 |
#endif |
974 |
#endif |
Lines 964-970
Link Here
|
964 |
propogateCSeq(pConn); |
990 |
propogateCSeq(pConn); |
965 |
int tSize = 0; |
991 |
int tSize = 0; |
966 |
char *tVol = getFromHeader(pConn->recv.data, "volume", &tSize); |
992 |
char *tVol = getFromHeader(pConn->recv.data, "volume", &tSize); |
967 |
slog(LOG_DEBUG_VV, "About to write [vol: %.*s] data to hairtunes\n", tSize, tVol); |
993 |
xprintf("About to write [vol: %.*s] data to hairtunes\n", tSize, tVol); |
968 |
// TBD VOLUME |
994 |
// TBD VOLUME |
969 |
#ifndef XBMC |
995 |
#ifndef XBMC |
970 |
write(pConn->hairtunes->in[1], "vol: ", 5); |
996 |
write(pConn->hairtunes->in[1], "vol: ", 5); |
Lines 973-983
Link Here
|
973 |
#else |
999 |
#else |
974 |
hairtunes_setvolume(atof(tVol)); |
1000 |
hairtunes_setvolume(atof(tVol)); |
975 |
#endif |
1001 |
#endif |
976 |
slog(LOG_DEBUG_VV, "Finished writing data write data to hairtunes\n"); |
1002 |
xprintf("Finished writing data write data to hairtunes\n"); |
977 |
} |
1003 |
} |
978 |
else |
1004 |
else |
979 |
{ |
1005 |
{ |
980 |
slog(LOG_DEBUG, "\n\nUn-Handled recv: %s\n", pConn->recv.data); |
1006 |
xprintf("\n\nUn-Handled recv: %s\n", pConn->recv.data); |
981 |
propogateCSeq(pConn); |
1007 |
propogateCSeq(pConn); |
982 |
} |
1008 |
} |
983 |
addToShairBuffer(&(pConn->resp), "\r\n"); |
1009 |
addToShairBuffer(&(pConn->resp), "\r\n"); |
Lines 1056-1062
Link Here
|
1056 |
char tName[100 + HWID_SIZE + 3]; |
1082 |
char tName[100 + HWID_SIZE + 3]; |
1057 |
if(strlen(pServerName) > tMaxServerName) |
1083 |
if(strlen(pServerName) > tMaxServerName) |
1058 |
{ |
1084 |
{ |
1059 |
slog(LOG_INFO,"Hey dog, we see you like long server names, " |
1085 |
xprintf("Hey dog, we see you like long server names, " |
1060 |
"so we put a strncat in our command so we don't buffer overflow, while you listen to your flow.\n" |
1086 |
"so we put a strncat in our command so we don't buffer overflow, while you listen to your flow.\n" |
1061 |
"We just used the first %d characters. Pick something shorter if you want\n", tMaxServerName); |
1087 |
"We just used the first %d characters. Pick something shorter if you want\n", tMaxServerName); |
1062 |
} |
1088 |
} |
Lines 1067-1073
Link Here
|
1067 |
strcat(tName, pHWStr); |
1093 |
strcat(tName, pHWStr); |
1068 |
strcat(tName, "@"); |
1094 |
strcat(tName, "@"); |
1069 |
strncat(tName, pServerName, tMaxServerName); |
1095 |
strncat(tName, pServerName, tMaxServerName); |
1070 |
slog(AVAHI_LOG_LEVEL, "Avahi/DNS-SD Name: %s\n", tName); |
1096 |
xprintf("Avahi/DNS-SD Name: %s\n", tName); |
1071 |
|
1097 |
|
1072 |
execlp("avahi-publish-service", "avahi-publish-service", tName, |
1098 |
execlp("avahi-publish-service", "avahi-publish-service", tName, |
1073 |
"_raop._tcp", tPort, "tp=UDP","sm=false","sv=false","ek=1","et=0,1", |
1099 |
"_raop._tcp", tPort, "tp=UDP","sm=false","sv=false","ek=1","et=0,1", |
Lines 1079-1090
Link Here
|
1079 |
perror("error"); |
1105 |
perror("error"); |
1080 |
} |
1106 |
} |
1081 |
|
1107 |
|
1082 |
slog(LOG_INFO, "Bad error... couldn't find or failed to run: avahi-publish-service OR dns-sd\n"); |
1108 |
xprintf("Bad error... couldn't find or failed to run: avahi-publish-service OR dns-sd\n"); |
1083 |
exit(1); |
1109 |
//exit(1); |
1084 |
} |
1110 |
} |
1085 |
else |
1111 |
else |
1086 |
{ |
1112 |
{ |
1087 |
slog(LOG_DEBUG_VV, "Avahi/DNS-SD started on PID: %d\n", tPid); |
1113 |
xprintf("Avahi/DNS-SD started on PID: %d\n", tPid); |
1088 |
} |
1114 |
} |
1089 |
return tPid; |
1115 |
return tPid; |
1090 |
} |
1116 |
} |
Lines 1092-1098
Link Here
|
1092 |
|
1118 |
|
1093 |
void printBufferInfo(struct shairbuffer *pBuf, int pLevel) |
1119 |
void printBufferInfo(struct shairbuffer *pBuf, int pLevel) |
1094 |
{ |
1120 |
{ |
1095 |
slog(pLevel, "Buffer: [%s] size: %d maxchars:%d\n", pBuf->data, pBuf->current, pBuf->maxsize/sizeof(char)); |
1121 |
xprintf("Buffer: [%s] size: %d maxchars:%d\n", pBuf->data, pBuf->current, pBuf->maxsize/sizeof(char)); |
1096 |
} |
1122 |
} |
1097 |
|
1123 |
|
1098 |
int getAvailChars(struct shairbuffer *pBuf) |
1124 |
int getAvailChars(struct shairbuffer *pBuf) |
Lines 1173-1179
Link Here
|
1173 |
{ |
1199 |
{ |
1174 |
va_list argp; |
1200 |
va_list argp; |
1175 |
va_start(argp, pFormat); |
1201 |
va_start(argp, pFormat); |
1176 |
vprintf(pFormat, argp); |
1202 |
xprintf(pFormat, argp); |
|
|
1203 |
//vprintf(pFormat, argp); |
1177 |
va_end(argp); |
1204 |
va_end(argp); |
1178 |
} |
1205 |
} |
1179 |
//#endif |
1206 |
//#endif |
Lines 1227-1235
Link Here
|
1227 |
{ |
1254 |
{ |
1228 |
if(pBuf->data != NULL) |
1255 |
if(pBuf->data != NULL) |
1229 |
{ |
1256 |
{ |
1230 |
slog(LOG_DEBUG_VV, "Hrm, buffer wasn't cleaned up....trying to free\n"); |
1257 |
xprintf("Hrm, buffer wasn't cleaned up....trying to free\n"); |
1231 |
free(pBuf->data); |
1258 |
free(pBuf->data); |
1232 |
slog(LOG_DEBUG_VV, "Free didn't seem to seg fault....huzzah\n"); |
1259 |
xprintf("Free didn't seem to seg fault....huzzah\n"); |
1233 |
} |
1260 |
} |
1234 |
pBuf->current = 0; |
1261 |
pBuf->current = 0; |
1235 |
pBuf->marker = 0; |
1262 |
pBuf->marker = 0; |
Lines 1287-1292
Link Here
|
1287 |
BIO *tBio = BIO_new_mem_buf(AIRPORT_PRIVATE_KEY, -1); |
1314 |
BIO *tBio = BIO_new_mem_buf(AIRPORT_PRIVATE_KEY, -1); |
1288 |
RSA *rsa = PEM_read_bio_RSAPrivateKey(tBio, NULL, NULL, NULL); //NULL, NULL, NULL); |
1315 |
RSA *rsa = PEM_read_bio_RSAPrivateKey(tBio, NULL, NULL, NULL); //NULL, NULL, NULL); |
1289 |
BIO_free(tBio); |
1316 |
BIO_free(tBio); |
1290 |
slog(RSA_LOG_LEVEL, "RSA Key: %d\n", RSA_check_key(rsa)); |
1317 |
xprintf("RSA Key: %d\n", RSA_check_key(rsa)); |
1291 |
return rsa; |
1318 |
return rsa; |
1292 |
} |
1319 |
} |