#include <errno.h>#include <string.h>#include <stdio.h>#include <unistd.h>#include <fcntl.h>#include <termios.h>#include <stdarg.h>#include <stdlib.h>#include <strings.h>#include <sys/time.h>#include <sys/types.h>#include <sys/socket.h>#include <sys/param.h>#include <sys/ioctl.h>#include "gwlib/gwlib.h"#include "smsc.h"#include "smsc_p.h"#include "alt_charsets.h"#include "sms.h"Include dependency graph for smsc_emi_x25.c:

Go to the source code of this file.
Defines | |
| #define | CRTSCTS 0 |
Functions | |
| int | get_data (SMSCenter *smsc, char *buff, int length) |
| int | put_data (SMSCenter *smsc, char *buff, int length, int is_backup) |
| int | memorybuffer_append_data (SMSCenter *smsc, char *buff, int length) |
| int | memorybuffer_insert_data (SMSCenter *smsc, char *buff, int length) |
| int | memorybuffer_has_rawmessage (SMSCenter *smsc, int type, char auth) |
| int | memorybuffer_cut_rawmessage (SMSCenter *smsc, char *buff, int length) |
| int | parse_rawmessage_to_msg (SMSCenter *smsc, Msg **msg, char *rawmessage, int length) |
| int | parse_msg_to_rawmessage (SMSCenter *smsc, Msg *msg, char *rawmessage, int length) |
| int | acknowledge_from_rawmessage (SMSCenter *smsc, char *rawmessage, int length) |
| int | parse_emi_to_iso88591 (char *from, char *to, int length, int alt_charset) |
| int | parse_iso88591_to_emi (char *from, char *to, int length, int alt_charset) |
| int | parse_binary_to_emi (char *from, char *to, int length) |
| int | at_dial (char *device, char *phonenum, char *at_prefix, time_t how_long) |
| int | guarantee_link (SMSCenter *smsc) |
| void | generate_checksum (const unsigned char *buffer, unsigned char *checksum_out) |
| int | wait_for_ack (SMSCenter *smsc, int op_type) |
| char | char_iso_to_sms (unsigned char from, int alt_charset) |
| char | char_sms_to_iso (unsigned char from, int alt_charset) |
| int | emi_open_connection (SMSCenter *smsc) |
| SMSCenter * | emi_open (char *phonenum, char *serialdevice, char *username, char *password) |
| int | emi_reopen (SMSCenter *smsc) |
| int | emi_close (SMSCenter *smsc) |
| int | emi_fill_ucp60_login (char *buf, char *OAdC, char *passwd) |
| int | emi_open_session (SMSCenter *smsc) |
| int | emi_open_connection_ip (SMSCenter *smsc) |
| int | emi_reopen_ip (SMSCenter *smsc) |
| int | emi_close_ip (SMSCenter *smsc) |
| int | emi_pending_smsmessage (SMSCenter *smsc) |
| int | emi_submit_msg (SMSCenter *smsc, Msg *omsg) |
| int | emi_receive_msg (SMSCenter *smsc, Msg **tmsg) |
|
|
Definition at line 88 of file smsc_emi_x25.c. |
|
||||||||||||||||
|
Definition at line 966 of file smsc_emi_x25.c. References debug(), SMSCenter::emi_current_msg_number, generate_checksum(), and put_data(). Referenced by emi_receive_msg(). 00968 {
00969
00970 char emivars[128][1024];
00971 char timestamp[2048], sender[2048], receiver[2048];
00972 char emitext[2048], isotext[2048];
00973 char *leftslash, *rightslash;
00974 int msgnbr;
00975 int tmpint;
00976 int is_backup = 0;
00977
00978 msgnbr = -1;
00979 memset(&sender, 0, sizeof(sender));
00980 memset(&receiver, 0, sizeof(receiver));
00981 memset(&emitext, 0, sizeof(emitext));
00982 memset(&isotext, 0, sizeof(isotext));
00983 memset(×tamp, 0, sizeof(timestamp));
00984
00985 strncpy(isotext, rawmessage, length);
00986 leftslash = isotext;
00987
00988 if (isotext[length - 1] == 'X')
00989 is_backup = 1;
00990
00991 for (tmpint = 0; leftslash != NULL; tmpint++) {
00992 rightslash = strchr(leftslash + 1, '/');
00993
00994 if (rightslash == NULL)
00995 rightslash = strchr(leftslash + 1, '\3');
00996
00997 if (rightslash == NULL)
00998 break;
00999
01000 *rightslash = '\0';
01001 strcpy(emivars[tmpint], leftslash + 1);
01002 leftslash = rightslash;
01003 }
01004
01005 /* BODY */
01006 sprintf(isotext, "A//%s:%s", emivars[4], emivars[18]);
01007 sprintf(isotext, "A//%s:", emivars[5]);
01008 is_backup = 0;
01009
01010 /* HEADER */
01011
01012 debug("bb.sms.emi", 0, "acknowledge: type = '%s'", emivars[3]);
01013
01014 sprintf(emitext, "%s/%05i/%s/%s", emivars[0], (int) strlen(isotext) + 17,
01015 "R", emivars[3]);
01016
01017 smsc->emi_current_msg_number = atoi(emivars[0]) + 1;
01018
01019 /* FOOTER */
01020 sprintf(timestamp, "%s/%s/", emitext, isotext);
01021 generate_checksum((unsigned char *)timestamp, (unsigned char *)receiver);
01022
01023 sprintf(sender, "%c%s/%s/%s%c", 0x02, emitext, isotext, receiver, 0x03);
01024 put_data(smsc, sender, strlen(sender), is_backup);
01025
01026 return msgnbr;
01027
01028 }
|
Here is the call graph for this function:

|
||||||||||||||||||||
|
Definition at line 472 of file smsc_emi_x25.c. References debug(), error(), info(), and kannel_cfmakeraw(). Referenced by emi_open_connection(). 00473 {
00474 char tmpbuff[1024];
00475 int howmanyread = 0;
00476 int thistime = 0;
00477 int redial;
00478 int fd = -1;
00479 int ret;
00480 time_t timestart;
00481 struct termios tios;
00482
00483 /* The time at the start of the function is used when
00484 determining whether we have used up our allotted
00485 dial time and have to abort. */
00486 time(×tart);
00487
00488 /* Open the device properly. Remember to set the
00489 access codes correctly. */
00490 fd = open(device, O_RDWR | O_NONBLOCK | O_NOCTTY);
00491 if (fd == -1) {
00492 error(errno, "at_dial: error opening character device <%s>", device);
00493 goto error;
00494 }
00495 tcflush(fd, TCIOFLUSH);
00496
00497 /* The speed initialisation is pretty important. */
00498 tcgetattr(fd, &tios);
00499 #if defined(B115200)
00500 cfsetospeed(&tios, B115200);
00501 cfsetispeed(&tios, B115200);
00502 #elif defined(B76800)
00503 cfsetospeed(&tios, B76800);
00504 cfsetispeed(&tios, B76800);
00505 #elif defined(B57600)
00506 cfsetospeed(&tios, B57600);
00507 cfsetispeed(&tios, B57600);
00508 #elif defined(B38400)
00509 cfsetospeed(&tios, B38400);
00510 cfsetispeed(&tios, B38400);
00511 #elif defined(B19200)
00512 cfsetospeed(&tios, B19200);
00513 cfsetispeed(&tios, B19200);
00514 #elif defined(B9600)
00515 cfsetospeed(&tios, B9600);
00516 cfsetispeed(&tios, B9600);
00517 #endif
00518 kannel_cfmakeraw(&tios);
00519 tios.c_cflag |= (HUPCL | CREAD | CRTSCTS);
00520 ret = tcsetattr(fd, TCSANOW, &tios);
00521 if (ret == -1) {
00522 error(errno, "EMI[X25]: at_dial: fail to set termios attribute");
00523 }
00524
00525 /* Dial using an AT command string. */
00526 for (redial = 1; redial; ) {
00527 info(0, "at_dial: dialing <%s> on <%s> for <%i> seconds",
00528 phonenum, device,
00529 (int)(how_long - (time(NULL) - timestart)));
00530
00531 /* Send AT dial request. */
00532 howmanyread = 0;
00533 sprintf(tmpbuff, "%s%s\r\n", at_prefix, phonenum);
00534 ret = write(fd, tmpbuff, strlen(tmpbuff)); /* errors... -mg */
00535 memset(&tmpbuff, 0, sizeof(tmpbuff));
00536
00537 /* Read the answer to the AT command and react accordingly. */
00538 for (; ; ) {
00539 /* We don't want to dial forever */
00540 if (how_long != 0 && time(NULL) > timestart + how_long)
00541 goto timeout;
00542
00543 /* We don't need more space for dialout */
00544 if (howmanyread >= (int) sizeof(tmpbuff))
00545 goto error;
00546
00547 /* We read 1 char a time so that we don't
00548 accidentally read past the modem chat and
00549 into the SMSC datastream -mg */
00550 thistime = read(fd, &tmpbuff[howmanyread], 1);
00551 if (thistime == -1) {
00552 if (errno == EAGAIN) continue;
00553 if (errno == EINTR) continue;
00554 goto error;
00555 } else {
00556 howmanyread += thistime;
00557 }
00558
00559 /* Search for the newline on the AT status line. */
00560 if (tmpbuff[howmanyread - 1] == '\r'
00561 || tmpbuff[howmanyread - 1] == '\n') {
00562
00563 /* XXX ADD ALL POSSIBLE CHAT STRINGS XXX */
00564
00565 if (strstr(tmpbuff, "CONNECT") != NULL) {
00566 debug("bb.sms.emi", 0, "at_dial: CONNECT");
00567 redial = 0;
00568 break;
00569
00570 } else if (strstr(tmpbuff, "NO CARRIER") != NULL) {
00571 debug("bb.sms.emi", 0, "at_dial: NO CARRIER");
00572 redial = 1;
00573 break;
00574
00575 } else if (strstr(tmpbuff, "BUSY") != NULL) {
00576 debug("bb.sms.emi", 0, "at_dial: BUSY");
00577 redial = 1;
00578 break;
00579
00580 } else if (strstr(tmpbuff, "NO DIALTONE") != NULL) {
00581 debug("bb.sms.emi", 0, "at_dial: NO DIALTONE");
00582 redial = 1;
00583 break;
00584
00585 }
00586
00587 } /* End of if lastchr=='\r'||'\n'. */
00588
00589 /* Thou shall not consume all system resources
00590 by repeatedly looping a strstr search when
00591 the string update latency is very high as it
00592 is in serial communication. -mg */
00593 usleep(1000);
00594
00595 } /* End of read loop. */
00596
00597 /* Thou shall not flood the modem with dial requests. -mg */
00598 sleep(1);
00599
00600 } /* End of dial loop. */
00601
00602 debug("bb.sms.emi", 0, "at_dial: done with dialing");
00603 return fd;
00604
00605 timeout:
00606 error(0, "at_dial timed out");
00607 close(fd);
00608 return -1;
00609
00610 error:
00611 error(0, "at_dial failed");
00612 close(fd);
00613 return -1;
00614 }
|
Here is the call graph for this function:

|
||||||||||||
|
Definition at line 1237 of file smsc_emi_x25.c. Referenced by parse_iso88591_to_emi(). 01238 {
01239
01240 switch ((char)from) {
01241
01242 case 'A':
01243 return 0x41;
01244 case 'B':
01245 return 0x42;
01246 case 'C':
01247 return 0x43;
01248 case 'D':
01249 return 0x44;
01250 case 'E':
01251 return 0x45;
01252 case 'F':
01253 return 0x46;
01254 case 'G':
01255 return 0x47;
01256 case 'H':
01257 return 0x48;
01258 case 'I':
01259 return 0x49;
01260 case 'J':
01261 return 0x4A;
01262 case 'K':
01263 return 0x4B;
01264 case 'L':
01265 return 0x4C;
01266 case 'M':
01267 return 0x4D;
01268 case 'N':
01269 return 0x4E;
01270 case 'O':
01271 return 0x4F;
01272 case 'P':
01273 return 0x50;
01274 case 'Q':
01275 return 0x51;
01276 case 'R':
01277 return 0x52;
01278 case 'S':
01279 return 0x53;
01280 case 'T':
01281 return 0x54;
01282 case 'U':
01283 return 0x55;
01284 case 'V':
01285 return 0x56;
01286 case 'W':
01287 return 0x57;
01288 case 'X':
01289 return 0x58;
01290 case 'Y':
01291 return 0x59;
01292 case 'Z':
01293 return 0x5A;
01294
01295 case 'a':
01296 return 0x61;
01297 case 'b':
01298 return 0x62;
01299 case 'c':
01300 return 0x63;
01301 case 'd':
01302 return 0x64;
01303 case 'e':
01304 return 0x65;
01305 case 'f':
01306 return 0x66;
01307 case 'g':
01308 return 0x67;
01309 case 'h':
01310 return 0x68;
01311 case 'i':
01312 return 0x69;
01313 case 'j':
01314 return 0x6A;
01315 case 'k':
01316 return 0x6B;
01317 case 'l':
01318 return 0x6C;
01319 case 'm':
01320 return 0x6D;
01321 case 'n':
01322 return 0x6E;
01323 case 'o':
01324 return 0x6F;
01325 case 'p':
01326 return 0x70;
01327 case 'q':
01328 return 0x71;
01329 case 'r':
01330 return 0x72;
01331 case 's':
01332 return 0x73;
01333 case 't':
01334 return 0x74;
01335 case 'u':
01336 return 0x75;
01337 case 'v':
01338 return 0x76;
01339 case 'w':
01340 return 0x77;
01341 case 'x':
01342 return 0x78;
01343 case 'y':
01344 return 0x79;
01345 case 'z':
01346 return 0x7A;
01347
01348 case '0':
01349 return 0x30;
01350 case '1':
01351 return 0x31;
01352 case '2':
01353 return 0x32;
01354 case '3':
01355 return 0x33;
01356 case '4':
01357 return 0x34;
01358 case '5':
01359 return 0x35;
01360 case '6':
01361 return 0x36;
01362 case '7':
01363 return 0x37;
01364 case '8':
01365 return 0x38;
01366 case '9':
01367 return 0x39;
01368 case ':':
01369 return 0x3A;
01370 case ';':
01371 return 0x3B;
01372 case '<':
01373 return 0x3C;
01374 case '=':
01375 return 0x3D;
01376 case '>':
01377 return 0x3E;
01378 case '?':
01379 return 0x3F;
01380
01381 case 'Ä':
01382 return '[';
01383 case 'Ö':
01384 return '\\';
01385 case 'Å':
01386 return 0x0E;
01387 case 'Ü':
01388 return ']';
01389 case 'ä':
01390 return '{';
01391 case 'ö':
01392 return '|';
01393 case 'å':
01394 return 0x0F;
01395 case 'ü':
01396 return '}';
01397 case 'ß':
01398 return '~';
01399 case '§':
01400 return '^';
01401 case 'Ñ':
01402 return 0x5F;
01403 case 'ø':
01404 return 0x0C;
01405
01406 /* case 'Delta': return 0x10; */
01407 /* case 'Fii': return 0x12; */
01408 /* case 'Lambda': return 0x13; */
01409 /* case 'Alpha': return 0x14; */
01410 /* case 'Omega': return 0x15; */
01411 /* case 'Pii': return 0x16; */
01412 /* case 'Pii': return 0x17; */
01413 /* case 'Delta': return 0x18; */
01414 /* case 'Delta': return 0x19; */
01415 /* case 'Delta': return 0x1A; */
01416
01417 case ' ':
01418 return 0x20;
01419 case '@':
01420 if (alt_charset == EMI_SWAPPED_CHARS)
01421 return 0x00;
01422 else
01423 return 0x40;
01424 case '£':
01425 return 0x01;
01426 case '$':
01427 return 0x24;
01428 case '¥':
01429 return 0x03;
01430 case 'è':
01431 return 0x04;
01432 case 'é':
01433 return 0x05;
01434 case 'ù':
01435 return 0x06;
01436 case 'ì':
01437 return 0x07;
01438 case 'ò':
01439 return 0x08;
01440 case 'Ç':
01441 return 0x09;
01442 case '\r':
01443 return 0x0A;
01444 case 'Ø':
01445 return 0x0B;
01446 case '\n':
01447 return 0x0D;
01448 case 'Æ':
01449 return 0x1C;
01450 case 'æ':
01451 return 0x1D;
01452 case 'É':
01453 return 0x1F;
01454
01455 case '!':
01456 return 0x21;
01457 case '"':
01458 return 0x22;
01459 case '#':
01460 return 0x23;
01461 case '¤':
01462 return 0x02;
01463 case '%':
01464 return 0x25;
01465
01466 case '&':
01467 return 0x26;
01468 case '\'':
01469 return 0x27;
01470 case '(':
01471 return 0x28;
01472 case ')':
01473 return 0x29;
01474 case '*':
01475 return 0x2A;
01476
01477 case '+':
01478 return 0x2B;
01479 case ',':
01480 return 0x2C;
01481 case '-':
01482 return 0x2D;
01483 case '.':
01484 return 0x2E;
01485 case '/':
01486 return 0x2F;
01487
01488 case '¿':
01489 return 0x60;
01490 case 'ñ':
01491 return 0x1E;
01492 case 'à':
01493 return 0x7F;
01494 case '¡':
01495 if (alt_charset == EMI_SWAPPED_CHARS)
01496 return 0x40;
01497 else
01498 return 0x00;
01499 case '_':
01500 return 0x11;
01501
01502 default:
01503 return 0x20; /* space */
01504
01505 } /* switch */
01506 }
|
|
||||||||||||
|
Definition at line 1513 of file smsc_emi_x25.c. Referenced by parse_emi_to_iso88591(). 01514 {
01515
01516 switch ((int)from) {
01517
01518 case 0x41:
01519 return 'A';
01520 case 0x42:
01521 return 'B';
01522 case 0x43:
01523 return 'C';
01524 case 0x44:
01525 return 'D';
01526 case 0x45:
01527 return 'E';
01528 case 0x46:
01529 return 'F';
01530 case 0x47:
01531 return 'G';
01532 case 0x48:
01533 return 'H';
01534 case 0x49:
01535 return 'I';
01536 case 0x4A:
01537 return 'J';
01538 case 0x4B:
01539 return 'K';
01540 case 0x4C:
01541 return 'L';
01542 case 0x4D:
01543 return 'M';
01544 case 0x4E:
01545 return 'N';
01546 case 0x4F:
01547 return 'O';
01548 case 0x50:
01549 return 'P';
01550 case 0x51:
01551 return 'Q';
01552 case 0x52:
01553 return 'R';
01554 case 0x53:
01555 return 'S';
01556 case 0x54:
01557 return 'T';
01558 case 0x55:
01559 return 'U';
01560 case 0x56:
01561 return 'V';
01562 case 0x57:
01563 return 'W';
01564 case 0x58:
01565 return 'X';
01566 case 0x59:
01567 return 'Y';
01568 case 0x5A:
01569 return 'Z';
01570
01571 case 0x61:
01572 return 'a';
01573 case 0x62:
01574 return 'b';
01575 case 0x63:
01576 return 'c';
01577 case 0x64:
01578 return 'd';
01579 case 0x65:
01580 return 'e';
01581 case 0x66:
01582 return 'f';
01583 case 0x67:
01584 return 'g';
01585 case 0x68:
01586 return 'h';
01587 case 0x69:
01588 return 'i';
01589 case 0x6A:
01590 return 'j';
01591 case 0x6B:
01592 return 'k';
01593 case 0x6C:
01594 return 'l';
01595 case 0x6D:
01596 return 'm';
01597 case 0x6E:
01598 return 'n';
01599 case 0x6F:
01600 return 'o';
01601 case 0x70:
01602 return 'p';
01603 case 0x71:
01604 return 'q';
01605 case 0x72:
01606 return 'r';
01607 case 0x73:
01608 return 's';
01609 case 0x74:
01610 return 't';
01611 case 0x75:
01612 return 'u';
01613 case 0x76:
01614 return 'v';
01615 case 0x77:
01616 return 'w';
01617 case 0x78:
01618 return 'x';
01619 case 0x79:
01620 return 'y';
01621 case 0x7A:
01622 return 'z';
01623
01624 case 0x30:
01625 return '0';
01626 case 0x31:
01627 return '1';
01628 case 0x32:
01629 return '2';
01630 case 0x33:
01631 return '3';
01632 case 0x34:
01633 return '4';
01634 case 0x35:
01635 return '5';
01636 case 0x36:
01637 return '6';
01638 case 0x37:
01639 return '7';
01640 case 0x38:
01641 return '8';
01642 case 0x39:
01643 return '9';
01644 case 0x3A:
01645 return ':';
01646 case 0x3B:
01647 return ';';
01648 case 0x3C:
01649 return '<';
01650 case 0x3D:
01651 return '=';
01652 case 0x3E:
01653 return '>';
01654 case 0x3F:
01655 return '?';
01656
01657 case '[':
01658 return 'Ä';
01659 case '\\':
01660 return 'Ö';
01661 case '\xC5':
01662 return 'Å';
01663 case ']':
01664 return 'Ü';
01665 case '{':
01666 return 'ä';
01667 case '|':
01668 return 'ö';
01669 case 0xE5:
01670 return 'å';
01671 case '}':
01672 return 'ü';
01673 case '~':
01674 return 'ß';
01675 case 0xA7:
01676 return '§';
01677 case 0xD1:
01678 return 'Ñ';
01679 case 0xF8:
01680 return 'ø';
01681
01682 /* case 'Delta': return 0x10; */
01683 /* case 'Fii': return 0x12; */
01684 /* case 'Lambda': return 0x13; */
01685 /* case 'Alpha': return 0x14; */
01686 /* case 'Omega': return 0x15; */
01687 /* case 'Pii': return 0x16; */
01688 /* case 'Pii': return 0x17; */
01689 /* case 'Delta': return 0x18; */
01690 /* case 'Delta': return 0x19; */
01691 /* case 'Delta': return 0x1A; */
01692
01693 case 0x20:
01694 return ' ';
01695 case 0x40:
01696 return '@';
01697 case 0xA3:
01698 return '£';
01699 case 0x24:
01700 return '$';
01701 case 0xA5:
01702 return '¥';
01703 case 0xE8:
01704 return 'è';
01705 case 0xE9:
01706 return 'é';
01707 case 0xF9:
01708 return 'ù';
01709 case 0xEC:
01710 return 'ì';
01711 case 0xF2:
01712 return 'ò';
01713 case 0xC7:
01714 return 'Ç';
01715 case 0x0A:
01716 return '\r';
01717 case 0xD8:
01718 return 'Ø';
01719 case 0x0D:
01720 return '\n';
01721 case 0xC6:
01722 return 'Æ';
01723 case 0xE6:
01724 return 'æ';
01725 case 0x1F:
01726 return 'É';
01727
01728 case 0x21:
01729 return '!';
01730 case 0x22:
01731 return '"';
01732 case 0x23:
01733 return '#';
01734 case 0xA4:
01735 return '¤';
01736 case 0x25:
01737 return '%';
01738
01739 case 0x26:
01740 return '&';
01741 case 0x27:
01742 return '\'';
01743 case 0x28:
01744 return '(';
01745 case 0x29:
01746 return ')';
01747 case 0x2A:
01748 return '*';
01749
01750 case 0x2B:
01751 return '+';
01752 case 0x2C:
01753 return ',';
01754 case 0x2D:
01755 return '-';
01756 case 0x2E:
01757 return '.';
01758 case 0x2F:
01759 return '/';
01760
01761 case 0xBF:
01762 return '¿';
01763 case 0xF1:
01764 return 'ñ';
01765 case 0xE0:
01766 return 'à';
01767 case 0xA1:
01768 return '¡';
01769 case 0x5F:
01770 return '_';
01771
01772 default:
01773 return ' ';
01774
01775 } /* switch */
01776 }
|
|
|
Definition at line 194 of file smsc_emi_x25.c. References emi_close_ip(). Referenced by emi_reopen(), and smsc_close(). 00195 {
00196 return emi_close_ip(smsc);
00197 }
|
Here is the call graph for this function:

|
|
Definition at line 302 of file smsc_emi_x25.c. References SMSCenter::emi_fd, and info(). Referenced by emi_close(), and emi_reopen_ip(). 00303 {
00304
00305 if (smsc->emi_fd == -1) {
00306 info(0, "Trying to close already closed EMI, ignoring");
00307 return 0;
00308 }
00309 close(smsc->emi_fd);
00310 smsc->emi_fd = -1;
00311
00312 return 0;
00313 }
|
Here is the call graph for this function:

|
||||||||||||||||
|
Definition at line 199 of file smsc_emi_x25.c. References error(), and parse_binary_to_emi(). Referenced by emi_open_session(). 00199 {
00200 int max_ia5passwd_len;
00201 char *ia5passwd;
00202
00203 max_ia5passwd_len = strlen(passwd) * 2 + 1;
00204 ia5passwd = gw_malloc(max_ia5passwd_len);
00205
00206 if (parse_binary_to_emi(passwd, ia5passwd, strlen(passwd)) < 0) {
00207 error(0, "parse_binary_to_emi failed");
00208 gw_free(ia5passwd);
00209 return -1;
00210 }
00211
00212 sprintf(buf, "%s/%c/%c/%c/%s//%s/////",
00213 OAdC, /* OAdC: Address code originator */
00214 '6', /* OTON: 6 = Abbreviated number (short number alias) */
00215 '5', /* ONPI: 5 = Private (TCP/IP address/abbreviated number address) */
00216 '1', /* STYP: 1 = open session */
00217 ia5passwd, /* PWD: Current password encoded into IA5 characters */
00218 "0100" /* VERS: Version number 0100 */
00219 );
00220
00221 gw_free(ia5passwd);
00222 return 0;
00223 }
|
Here is the call graph for this function:

|
||||||||||||||||||||
|
Definition at line 153 of file smsc_emi_x25.c. References SMSCenter::emi_current_msg_number, emi_open_connection(), SMSCenter::emi_password, SMSCenter::emi_phonenum, SMSCenter::emi_serialdevice, SMSCenter::emi_username, error(), SMSCenter::name, password, smscenter_construct(), smscenter_destruct(), SMSCenter::type, and username. Referenced by smsc_open(). 00154 {
00155 SMSCenter *smsc;
00156
00157 smsc = smscenter_construct();
00158 if (smsc == NULL)
00159 goto error;
00160
00161 smsc->type = SMSC_TYPE_EMI_X25;
00162
00163 smsc->emi_phonenum = gw_strdup(phonenum);
00164 smsc->emi_serialdevice = gw_strdup(serialdevice);
00165 smsc->emi_username = gw_strdup(username);
00166 smsc->emi_password = gw_strdup(password);
00167
00168 smsc->emi_current_msg_number = 0;
00169
00170 if (emi_open_connection(smsc) < 0)
00171 goto error;
00172
00173 sprintf(smsc->name, "EMI:%s:%s", smsc->emi_phonenum,
00174 smsc->emi_username);
00175 return smsc;
00176
00177 error:
00178 error(0, "emi_open failed");
00179 smscenter_destruct(smsc);
00180 return NULL;
00181 }
|
Here is the call graph for this function:

|
|
Definition at line 138 of file smsc_emi_x25.c. References at_dial(), SMSCenter::emi_fd, SMSCenter::emi_phonenum, and SMSCenter::emi_serialdevice. Referenced by emi_open(), emi_reopen(), and guarantee_link(). 00139 {
00140 char tmpbuff[1024];
00141
00142 sprintf(tmpbuff, "/dev/%s", smsc->emi_serialdevice);
00143 smsc->emi_fd = at_dial(tmpbuff, smsc->emi_phonenum, "ATD", 30);
00144
00145 if (smsc->emi_fd <= 0)
00146 return -1;
00147
00148 return 0;
00149 }
|
Here is the call graph for this function:

|
|
Definition at line 276 of file smsc_emi_x25.c. References SMSCenter::emi_fd, SMSCenter::emi_hostname, emi_open_session(), SMSCenter::emi_our_port, SMSCenter::emi_password, SMSCenter::emi_port, SMSCenter::emi_username, and tcpip_connect_to_server_with_port(). Referenced by emi_reopen_ip(). 00277 {
00278 smsc->emi_fd =
00279 tcpip_connect_to_server_with_port(smsc->emi_hostname,
00280 smsc->emi_port, smsc->emi_our_port,
00281 NULL);
00282 /* XXX add interface_name if required */
00283 if (smsc->emi_fd < 0)
00284 return -1;
00285
00286 if (smsc->emi_username && smsc->emi_password) {
00287 return emi_open_session(smsc);
00288 }
00289
00290 return 0;
00291 }
|
Here is the call graph for this function:

|
|
Definition at line 225 of file smsc_emi_x25.c. References debug(), SMSCenter::emi_current_msg_number, emi_fill_ucp60_login(), SMSCenter::emi_password, SMSCenter::emi_username, error(), generate_checksum(), info(), put_data(), and wait_for_ack(). Referenced by emi_open_connection_ip(). 00226 {
00227 char message_whole [1024];
00228 char message_body [1024];
00229 char message_header [50];
00230 char message_footer [10];
00231 char my_buffer [1024];
00232 int length;
00233
00234 memset(message_whole, 0, sizeof(message_whole));
00235 memset(message_body, 0, sizeof(message_body));
00236 memset(message_header, 0, sizeof(message_header));
00237 memset(message_footer, 0, sizeof(message_footer));
00238
00239 if (emi_fill_ucp60_login(message_body, smsc->emi_username, smsc->emi_password) < 0) {
00240 error(0, "emi_fill_ucp60_login failed");
00241 return -1;
00242 }
00243
00244 length = strlen(message_body);
00245 length += 13; /* header (fixed) */
00246 length += 2; /* footer (fixed) */
00247 length += 2; /* slashes between header, body, footer */
00248
00249 sprintf(message_header, "%02i/%05i/O/60",
00250 (smsc->emi_current_msg_number++ % 100), length);
00251
00252 /* FOOTER */
00253
00254 sprintf(my_buffer, "%s/%s/", message_header, message_body);
00255 generate_checksum((unsigned char *)my_buffer, (unsigned char *)message_footer);
00256
00257 sprintf(message_whole, "\x02%s/%s/%s\x03", message_header,
00258 message_body, message_footer);
00259
00260 debug("bb.sms.emi", 0, "final UCP60 msg: <%s>", message_whole);
00261
00262 put_data(smsc, message_whole, strlen(message_whole), 0);
00263
00264 if (!wait_for_ack(smsc, 60)) {
00265 info(0, "emi_open_session: wait for ack failed!");
00266 return -1;
00267 }
00268
00269 return 0;
00270 }
|
Here is the call graph for this function:

|
|
Definition at line 319 of file smsc_emi_x25.c. References get_data(), guarantee_link(), memorybuffer_cut_rawmessage(), memorybuffer_has_rawmessage(), and memorybuffer_insert_data(). Referenced by smscenter_pending_smsmessage(). 00320 {
00321
00322 char *tmpbuff;
00323 int n = 0;
00324 /* time_t timenow; */
00325
00326 /* Block until we have a connection */
00327 guarantee_link(smsc);
00328
00329 /* If we have MO-message, then act (return 1) */
00330 if (memorybuffer_has_rawmessage(smsc, 52, 'O') > 0 ||
00331 memorybuffer_has_rawmessage(smsc, 1, 'O') > 0 )
00332 return 1;
00333
00334 tmpbuff = gw_malloc(10 * 1024);
00335 memset(tmpbuff, 0, 10*1024);
00336
00337 /* check for data */
00338 n = get_data(smsc, tmpbuff, 10 * 1024);
00339 if (n > 0)
00340 memorybuffer_insert_data(smsc, tmpbuff, n);
00341
00342 /* delete all ACKs/NACKs/whatever */
00343 while (memorybuffer_has_rawmessage(smsc, 51, 'R') > 0 ||
00344 memorybuffer_has_rawmessage(smsc, 1, 'R') > 0)
00345 memorybuffer_cut_rawmessage(smsc, tmpbuff, 10*1024);
00346
00347 gw_free(tmpbuff);
00348
00349 /* If we have MO-message, then act (return 1) */
00350
00351 if (memorybuffer_has_rawmessage(smsc, 52, 'O') > 0 ||
00352 memorybuffer_has_rawmessage(smsc, 1, 'O') > 0)
00353 return 1;
00354
00355 /*
00356 time(&timenow);
00357 if( (smsc->emi_last_spoke + 60*20) < timenow) {
00358 time(&smsc->emi_last_spoke);
00359 }
00360 */
00361
00362 return 0;
00363
00364 }
|
Here is the call graph for this function:

|
||||||||||||
|
Definition at line 408 of file smsc_emi_x25.c. References acknowledge_from_rawmessage(), error(), memorybuffer_cut_rawmessage(), msg_destroy(), and parse_rawmessage_to_msg(). Referenced by smscenter_receive_msg(). 00409 {
00410 char *tmpbuff;
00411 Msg *msg = NULL;
00412
00413 *tmsg = NULL;
00414
00415 tmpbuff = gw_malloc(10 * 1024);
00416 memset(tmpbuff, 0, 10*1024);
00417
00418 /* get and delete message from buffer */
00419 memorybuffer_cut_rawmessage(smsc, tmpbuff, 10*1024);
00420 parse_rawmessage_to_msg(smsc, &msg, tmpbuff, strlen(tmpbuff));
00421
00422 /* yeah yeah, I got the message... */
00423 acknowledge_from_rawmessage(smsc, tmpbuff, strlen(tmpbuff));
00424
00425 /* return with the joyful news */
00426 gw_free(tmpbuff);
00427
00428 if (msg == NULL) goto error;
00429
00430 *tmsg = msg;
00431
00432 return 1;
00433
00434 error:
00435 gw_free(tmpbuff);
00436 msg_destroy(msg);
00437 return -1;
00438 }
|
Here is the call graph for this function:

|
|
Definition at line 183 of file smsc_emi_x25.c. References emi_close(), emi_open_connection(), and error(). Referenced by smsc_reopen(). 00184 {
00185 emi_close(smsc);
00186
00187 if (emi_open_connection(smsc) < 0) {
00188 error(0, "emi_reopen failed");
00189 return -1;
00190 }
00191 return 0;
00192 }
|
Here is the call graph for this function:

|
|
Definition at line 294 of file smsc_emi_x25.c. References emi_close_ip(), and emi_open_connection_ip(). 00295 {
00296 emi_close_ip(smsc);
00297
00298 return emi_open_connection_ip(smsc);
00299 }
|
Here is the call graph for this function:

|
||||||||||||
|
Definition at line 372 of file smsc_emi_x25.c. References debug(), error(), info(), parse_msg_to_rawmessage(), put_data(), and wait_for_ack(). Referenced by smscenter_submit_msg(). 00373 {
00374 char *tmpbuff = NULL;
00375
00376 if (smsc == NULL) goto error;
00377 if (omsg == NULL) goto error;
00378
00379 tmpbuff = gw_malloc(10 * 1024);
00380 memset(tmpbuff, 0, 10*1024);
00381
00382 if (parse_msg_to_rawmessage(smsc, omsg, tmpbuff, 10*1024) < 1)
00383 goto error;
00384
00385 if (put_data(smsc, tmpbuff, strlen(tmpbuff), 0) < 0) {
00386 info(0, "put_data failed!");
00387 goto error;
00388 }
00389
00390 wait_for_ack(smsc, 51);
00391
00392 /* smsc->emi_current_msg_number += 1; */
00393 debug("bb.sms.emi", 0, "Submit Ok...");
00394
00395 gw_free(tmpbuff);
00396 return 0;
00397
00398 error:
00399 debug("bb.sms.emi", 0, "Submit Error...");
00400
00401 gw_free(tmpbuff);
00402 return -1;
00403 }
|
Here is the call graph for this function:

|
||||||||||||
|
Definition at line 1215 of file smsc_emi_x25.c. Referenced by acknowledge_from_rawmessage(), emi_open_session(), and parse_msg_to_rawmessage(). 01216 {
01217 const unsigned char *p;
01218 int j;
01219
01220 j = 0;
01221 for (p = buf; *p != '\0'; p++) {
01222 j += *p;
01223
01224 if (j >= 256)
01225 j -= 256;
01226 }
01227
01228 sprintf((char *)out, "%02X", j);
01229 }
|
|
||||||||||||||||
|
Definition at line 660 of file smsc_emi_x25.c. References SMSCenter::buffer, debug(), SMSCenter::emi_backup_allow_ip, SMSCenter::emi_backup_fd, SMSCenter::emi_fd, SMSCenter::emi_secondary_fd, error(), host_ip(), info(), is_allowed_ip(), octstr_create, octstr_destroy(), octstr_get_cstr, octstr_imm(), and SMSCenter::type. Referenced by emi_pending_smsmessage(), and wait_for_ack(). 00661 {
00662 int n = 0;
00663
00664 struct sockaddr_in client_addr;
00665 socklen_t client_addr_len;
00666
00667 fd_set rf;
00668 struct timeval to;
00669 int ret;
00670
00671 memset(buff, 0, length);
00672
00673 if (smsc->type == SMSC_TYPE_EMI_X25) {
00674 tcdrain(smsc->emi_fd);
00675 n = read(smsc->emi_fd, buff, length);
00676 return n;
00677 }
00678
00679 FD_ZERO(&rf);
00680 if (smsc->emi_fd >= 0) FD_SET(smsc->emi_fd, &rf);
00681 if (smsc->emi_secondary_fd >= 0) FD_SET(smsc->emi_secondary_fd, &rf);
00682 if (smsc->emi_backup_fd > 0) FD_SET(smsc->emi_backup_fd, &rf);
00683
00684 FD_SET(0, &rf);
00685 to.tv_sec = 0;
00686 to.tv_usec = 100;
00687
00688 ret = select(FD_SETSIZE, &rf, NULL, NULL, &to);
00689
00690 if (ret > 0) {
00691 if (smsc->emi_secondary_fd >= 0 && FD_ISSET(smsc->emi_secondary_fd, &rf)) {
00692 n = read(smsc->emi_secondary_fd, buff, length - 1);
00693
00694 if (n == -1) {
00695 error(errno, "Error - Secondary socket closed");
00696 close(smsc->emi_secondary_fd);
00697 smsc->emi_secondary_fd = -1;
00698 } else if (n == 0) {
00699 info(0, "Secondary socket closed by SMSC");
00700 close(smsc->emi_secondary_fd);
00701 smsc->emi_secondary_fd = -1;
00702 } else { /* UGLY! We put 'X' after message */
00703 buff[n] = 'X'; /* if it is from secondary fd!!! */
00704 n++;
00705 }
00706 } else if (smsc->emi_fd >= 0 && FD_ISSET(smsc->emi_fd, &rf)) {
00707 n = read(smsc->emi_fd, buff, length);
00708 if (n == 0) {
00709 close(smsc->emi_fd);
00710 info(0, "Main EMI socket closed by SMSC");
00711 smsc->emi_fd = -1; /* ready to be re-opened */
00712 }
00713 }
00714 if ((smsc->emi_backup_fd > 0) && FD_ISSET(smsc->emi_backup_fd, &rf)) {
00715 if (smsc->emi_secondary_fd == -1) {
00716 Octstr *ip, *allow;
00717
00718 smsc->emi_secondary_fd = accept(smsc->emi_backup_fd,
00719 (struct sockaddr *)&client_addr, &client_addr_len);
00720
00721 ip = host_ip(client_addr);
00722 if (smsc->emi_backup_allow_ip == NULL)
00723 allow = NULL;
00724 else
00725 allow = octstr_create(smsc->emi_backup_allow_ip);
00726 if (is_allowed_ip(allow, octstr_imm("*.*.*.*"), ip) == 0) {
00727 info(0, "SMSC secondary connection tried from <%s>, "
00728 "disconnected",
00729 octstr_get_cstr(ip));
00730 octstr_destroy(ip);
00731 octstr_destroy(allow);
00732 close(smsc->emi_secondary_fd);
00733 smsc->emi_secondary_fd = -1;
00734 return 0;
00735 }
00736 info(0, "Secondary socket opened by SMSC from <%s>",
00737 octstr_get_cstr(ip));
00738 octstr_destroy(ip);
00739 octstr_destroy(allow);
00740 } else
00741 info(0, "New connection request while old secondary is open!");
00742 }
00743 }
00744 if (n > 0) {
00745 debug("bb.sms.emi", 0, "get_data:Read %d bytes: <%.*s>", n, n, buff);
00746 debug("bb.sms.emi", 0, "get_data:smsc->buffer == <%s>", smsc->buffer);
00747 }
00748 return n;
00749
00750 }
|
Here is the call graph for this function:

|
|
Definition at line 449 of file smsc_emi_x25.c. References SMSCenter::buffer, SMSCenter::buflen, SMSCenter::bufsize, and emi_open_connection(). Referenced by emi_pending_smsmessage(). 00450 {
00451 int need_to_connect = 0;
00452
00453 /* If something is obviously wrong. */
00454 if (strstr(smsc->buffer, "OK")) need_to_connect = 1;
00455 if (strstr(smsc->buffer, "NO CARRIER")) need_to_connect = 1;
00456 if (strstr(smsc->buffer, "NO DIALTONE")) need_to_connect = 1;
00457
00458 /* Clear the buffer */
00459 while (need_to_connect) {
00460 /* Connect */
00461 need_to_connect = emi_open_connection(smsc) < 0;
00462
00463 /* Clear the buffer so that the next call to guarantee
00464 doesn't find the "NO CARRIER" string again. */
00465 smsc->buflen = 0;
00466 memset(smsc->buffer, 0, smsc->bufsize);
00467 }
00468
00469 return 0;
00470 }
|
Here is the call graph for this function:

|
||||||||||||||||
|
Definition at line 794 of file smsc_emi_x25.c. References SMSCenter::buffer, SMSCenter::buflen, and SMSCenter::bufsize. Referenced by wait_for_ack(). 00795 {
00796 while (smsc->bufsize < (smsc->buflen + length)) { /* buffer too small */
00797 char *p = gw_realloc(smsc->buffer, smsc->bufsize * 2);
00798 smsc->buffer = p;
00799 smsc->bufsize *= 2;
00800 }
00801
00802 memcpy(smsc->buffer + smsc->buflen, buff, length);
00803 smsc->buflen += length;
00804 return 0;
00805
00806 }
|
|
||||||||||||||||
|
Definition at line 857 of file smsc_emi_x25.c. References SMSCenter::buffer, SMSCenter::buflen, SMSCenter::bufsize, and error(). Referenced by emi_pending_smsmessage(), emi_receive_msg(), and wait_for_ack(). 00858 {
00859
00860 char *stx, *etx;
00861 int size_of_cut_piece;
00862 int size_of_the_rest;
00863
00864 /* We don't check for NULLs since we're sure that nobody has fooled
00865 around with smsc->buffer since has_rawmessage was last called... */
00866
00867 stx = memchr(smsc->buffer, '\2', smsc->buflen);
00868 etx = memchr(smsc->buffer, '\3', smsc->buflen);
00869
00870 if (*(etx + 1) == 'X') /* secondary! UGLY KLUDGE */
00871 etx++;
00872
00873 size_of_cut_piece = (etx - stx) + 1;
00874 size_of_the_rest = (smsc->buflen - size_of_cut_piece);
00875
00876 if (length < size_of_cut_piece) {
00877 error(0, "the buffer you provided for cutting was too small");
00878 return -1;
00879 }
00880
00881 /* move the part before our magic rawmessage to the safe house */
00882 memcpy(buff, stx, size_of_cut_piece);
00883 buff[size_of_cut_piece] = '\0'; /* NULL-terminate */
00884
00885 /* move the stuff in membuffer one step down */
00886 memmove(stx, etx + 1, (smsc->buffer + smsc->bufsize) - stx );
00887
00888 smsc->buflen -= size_of_cut_piece;
00889
00890 return 0;
00891
00892 }
|
Here is the call graph for this function:

|
||||||||||||||||
|
Definition at line 828 of file smsc_emi_x25.c. References SMSCenter::buffer, SMSCenter::buflen, debug(), and type. Referenced by emi_pending_smsmessage(), and wait_for_ack(). 00829 {
00830 char tmpbuff[1024], tmpbuff2[1024];
00831 char *stx, *etx;
00832
00833 stx = memchr(smsc->buffer, '\2', smsc->buflen);
00834 etx = memchr(smsc->buffer, '\3', smsc->buflen);
00835
00836 if (stx && etx && stx < etx) {
00837 strncpy(tmpbuff, stx, etx - stx + 1);
00838 tmpbuff[etx - stx + 1] = '\0';
00839 if (auth)
00840 sprintf(tmpbuff2, "/%c/%02i/", auth, type);
00841 else
00842 sprintf(tmpbuff2, "/%02i/", type);
00843
00844 if (strstr(tmpbuff, tmpbuff2) != NULL) {
00845 debug("bb.sms.emi", 0, "found message <%c/%02i>...msg <%s>", auth, type, tmpbuff);
00846 return 1;
00847 }
00848 }
00849 return 0;
00850
00851 }
|
Here is the call graph for this function:

|
||||||||||||||||
|
Definition at line 811 of file smsc_emi_x25.c. References SMSCenter::buffer, SMSCenter::buflen, and SMSCenter::bufsize. Referenced by emi_pending_smsmessage(). 00812 {
00813 while (smsc->bufsize < (smsc->buflen + length)) { /* buffer too small */
00814 char *p = gw_realloc(smsc->buffer, smsc->bufsize * 2);
00815 smsc->buffer = p;
00816 smsc->bufsize *= 2;
00817 }
00818 memmove(smsc->buffer + length, smsc->buffer, smsc->buflen);
00819 memcpy(smsc->buffer, buff, length);
00820 smsc->buflen += length;
00821 return 0;
00822
00823 }
|
|
||||||||||||||||
|
Definition at line 1193 of file smsc_emi_x25.c. Referenced by emi_fill_ucp60_login(), and parse_msg_to_rawmessage(). 01194 {
01195 char buf[10];
01196 char *ptr;
01197
01198 if (!from || !to || length <= 0)
01199 return -1;
01200
01201 *to = '\0';
01202
01203 for (ptr = from; length > 0; ptr++, length--) {
01204 sprintf(buf, "%02X", (unsigned char)*ptr);
01205 strncat(to, buf, 2);
01206 }
01207
01208 return 0;
01209 }
|
|
||||||||||||||||||||
|
Definition at line 1146 of file smsc_emi_x25.c. References char_sms_to_iso(). Referenced by parse_rawmessage_to_msg(). 01148 {
01149 int hmtg = 0;
01150 unsigned int mychar;
01151 char tmpbuff[128];
01152
01153 for (hmtg = 0; hmtg <= (int)strlen(from); hmtg += 2) {
01154 strncpy(tmpbuff, from + hmtg, 2);
01155 sscanf(tmpbuff, "%x", &mychar);
01156 to[hmtg / 2] = char_sms_to_iso(mychar, alt_charset);
01157 }
01158
01159 to[(hmtg / 2)-1] = '\0';
01160
01161 return 0;
01162
01163 }
|
Here is the call graph for this function:

|
||||||||||||||||||||
|
Definition at line 1168 of file smsc_emi_x25.c. References char_iso_to_sms(), and debug(). Referenced by parse_msg_to_rawmessage(). 01170 {
01171 char buf[10];
01172 unsigned char tmpchar;
01173 char *ptr;
01174
01175 if (!from || !to || length <= 0)
01176 return -1;
01177
01178 *to = '\0';
01179
01180 debug("bb.sms.emi", 0, "emi parsing <%s> to emi, length %d", from, length);
01181
01182 for (ptr = from; length > 0; ptr++, length--) {
01183 tmpchar = char_iso_to_sms(*ptr, alt_charset);
01184 sprintf(buf, "%02X", tmpchar);
01185 strncat(to, buf, 2);
01186 }
01187 return 0;
01188 }
|
Here is the call graph for this function:

|
||||||||||||||||||||
|
Definition at line 1034 of file smsc_emi_x25.c. References SMSCenter::alt_charset, DC_7BIT, debug(), SMSCenter::emi_current_msg_number, generate_checksum(), octstr_get_char(), octstr_get_cstr, octstr_get_many_chars(), octstr_len(), parse_binary_to_emi(), parse_iso88591_to_emi(), and SMSCenter::type. Referenced by emi_submit_msg(). 01035 {
01036 char message_whole[10*1024];
01037 char message_body[10*1024];
01038 char message_header[1024];
01039 char message_footer[1024];
01040
01041 char my_buffer[10*1024];
01042 char my_buffer2[10*1024];
01043 char msgtext[1024];
01044 int length;
01045 char mt;
01046 char mcl[20];
01047 char snumbits[20];
01048 char xser[1024];
01049 int udh_len;
01050
01051 memset(&message_whole, 0, sizeof(message_whole));
01052 memset(&message_body, 0, sizeof(message_body));
01053 memset(&message_header, 0, sizeof(message_header));
01054 memset(&message_footer, 0, sizeof(message_footer));
01055 memset(&my_buffer, 0, sizeof(my_buffer));
01056 memset(&my_buffer2, 0, sizeof(my_buffer2));
01057 mt = '3';
01058 memset(&snumbits, 0, sizeof(snumbits));
01059 memset(&xser, 0, sizeof(xser));
01060
01061 /* XXX parse_iso88591_to_emi shouldn't use NUL terminated
01062 * strings, but Octstr directly, or a char* and a length.
01063 */
01064 if (octstr_len(msg->sms.udhdata)) {
01065 char xserbuf[258];
01066 /* we need a properly formated UDH here, there first byte contains his length
01067 * this will be formatted in the xser field of the EMI Protocol
01068 */
01069 udh_len = octstr_get_char(msg->sms.udhdata, 0) + 1;
01070 xserbuf[0] = 1;
01071 xserbuf[1] = udh_len;
01072 octstr_get_many_chars(&xserbuf[2], msg->sms.udhdata, 0, udh_len);
01073 parse_binary_to_emi(xserbuf, xser, udh_len + 2);
01074 } else {
01075 udh_len = 0;
01076 }
01077
01078 if (msg->sms.coding == DC_7BIT || msg->sms.coding == DC_UNDEF) {
01079 octstr_get_many_chars(msgtext, msg->sms.msgdata, 0, octstr_len(msg->sms.msgdata));
01080 msgtext[octstr_len(msg->sms.msgdata)] = '\0';
01081 parse_iso88591_to_emi(msgtext, my_buffer2,
01082 octstr_len(msg->sms.msgdata),
01083 smsc->alt_charset);
01084
01085 strcpy(snumbits, "");
01086 mt = '3';
01087 strcpy(mcl, "");
01088 } else {
01089 octstr_get_many_chars(msgtext, msg->sms.msgdata, 0, octstr_len(msg->sms.msgdata));
01090
01091 parse_binary_to_emi(msgtext, my_buffer2, octstr_len(msg->sms.msgdata));
01092
01093 sprintf(snumbits, "%04ld", octstr_len(msg->sms.msgdata)*8);
01094 mt = '4';
01095 strcpy(mcl, "1");
01096 }
01097
01098 /* XXX Where is DCS ? Is it in XSER like in emi2 ?
01099 * Please someone encode it with fields_to_dcs
01100 */
01101
01102 sprintf(message_body,
01103 "%s/%s/%s/%s/%s//%s////////////%c/%s/%s////%s//////%s//",
01104 octstr_get_cstr(msg->sms.receiver),
01105 msg->sms.sender ? octstr_get_cstr(msg->sms.sender) : "",
01106 "",
01107 "",
01108 "",
01109 "0100",
01110 mt,
01111 snumbits,
01112 my_buffer2,
01113 mcl,
01114 xser);
01115
01116 /* HEADER */
01117
01118 length = strlen(message_body);
01119 length += 13; /* header (fixed) */
01120 length += 2; /* footer (fixed) */
01121 length += 2; /* slashes between header, body, footer */
01122
01123 sprintf(message_header, "%02i/%05i/%s/%s", (smsc->emi_current_msg_number++ % 100), length, "O", "51");
01124
01125 /* FOOTER */
01126
01127 sprintf(my_buffer, "%s/%s/", message_header, message_body);
01128 generate_checksum((unsigned char *)my_buffer, (unsigned char *)message_footer);
01129
01130 sprintf(message_whole, "%c%s/%s/%s%c", 0x02, message_header, message_body, message_footer, 0x03);
01131
01132 strncpy(rawmessage, message_whole, rawmessage_length);
01133
01134 if (smsc->type == SMSC_TYPE_EMI_X25) {
01135 /* IC3S braindead EMI stack chokes on this... must fix it at the next time... */
01136 strcat(rawmessage, "\r");
01137 }
01138 debug("bb.sms.emi", 0, "emi %d message %s",
01139 smsc->emi_current_msg_number, rawmessage);
01140 return strlen(rawmessage);
01141 }
|
Here is the call graph for this function:

|
||||||||||||||||||||
|
Definition at line 897 of file smsc_emi_x25.c. References SMSCenter::alt_charset, error(), msg_create, octstr_create, parse_emi_to_iso88591(), and sms. Referenced by emi_receive_msg(). 00899 {
00900
00901 char emivars[128][1024];
00902 char *leftslash, *rightslash;
00903 char isotext[2048];
00904 int msgnbr;
00905 int tmpint;
00906
00907 msgnbr = -1;
00908
00909 memset(isotext, 0, sizeof(isotext));
00910
00911 strncpy(isotext, rawmessage, length);
00912 leftslash = isotext;
00913
00914 for (tmpint = 0; leftslash != NULL; tmpint++) {
00915 rightslash = strchr(leftslash + 1, '/');
00916
00917 if (rightslash == NULL)
00918 rightslash = strchr(leftslash + 1, '\3');
00919
00920 if (rightslash == NULL)
00921 break;
00922
00923 *rightslash = '\0';
00924 strcpy(emivars[tmpint], leftslash + 1);
00925 leftslash = rightslash;
00926 }
00927
00928 if (strcmp(emivars[3], "01") == 0) {
00929 if (strcmp(emivars[7], "2") == 0) {
00930 strcpy(isotext, emivars[8]);
00931 } else if (strcmp(emivars[7], "3") == 0) {
00932 parse_emi_to_iso88591(emivars[8], isotext, sizeof(isotext),
00933 smsc->alt_charset);
00934 } else {
00935 error(0, "Unknown 01-type EMI SMS (%s)", emivars[7]);
00936 strcpy(isotext, "");
00937 }
00938 } else if (strcmp(emivars[3], "51") == 0) {
00939 parse_emi_to_iso88591(emivars[24], isotext, sizeof(isotext),
00940 smsc->alt_charset);
00941 } else if (strcmp(emivars[3], "52") == 0) {
00942 parse_emi_to_iso88591(emivars[24], isotext, sizeof(isotext),
00943 smsc->alt_charset);
00944 } else {
00945 error(0, "HEY WE SHOULD NOT BE HERE!! Type = %s", emivars[3]);
00946 strcpy(isotext, "");
00947 }
00948
00949 *msg = msg_create(sms);
00950 if (*msg == NULL) goto error;
00951
00952 (*msg)->sms.sender = octstr_create(emivars[5]);
00953 (*msg)->sms.receiver = octstr_create(emivars[4]);
00954 (*msg)->sms.msgdata = octstr_create(isotext);
00955 (*msg)->sms.udhdata = NULL;
00956
00957 return msgnbr;
00958
00959 error:
00960 return -1;
00961 }
|
Here is the call graph for this function:

|
||||||||||||||||||||
|
Definition at line 755 of file smsc_emi_x25.c. References SMSCenter::emi_fd, error(), and SMSCenter::type. Referenced by acknowledge_from_rawmessage(), emi_open_session(), and emi_submit_msg(). 00756 {
00757 size_t len = length;
00758 int ret;
00759 int fd = -1;
00760
00761 fd = smsc->emi_fd;
00762 tcdrain(smsc->emi_fd);
00763
00764 /* Write until all data has been successfully written to the fd. */
00765 while (len > 0) {
00766 ret = write(fd, buff, len);
00767 if (ret == -1) {
00768 if (errno == EINTR) continue;
00769 if (errno == EAGAIN) continue;
00770 error(errno, "Writing to fd failed");
00771 return -1;
00772 }
00773 /* ret may be less than len, if the writing
00774 was interrupted by a signal. */
00775 len -= ret;
00776 buff += ret;
00777 }
00778
00779 if (smsc->type == SMSC_TYPE_EMI_X25) {
00780 /* Make sure the data gets written immediately.
00781 Wait a while just to add some latency so
00782 that the modem (or the UART) doesn't choke
00783 on the data. */
00784 tcdrain(smsc->emi_fd);
00785 usleep(1000);
00786 }
00787
00788 return 0;
00789 }
|
Here is the call graph for this function:

|
||||||||||||
|
Definition at line 621 of file smsc_emi_x25.c. References debug(), get_data(), memorybuffer_append_data(), memorybuffer_cut_rawmessage(), and memorybuffer_has_rawmessage(). Referenced by emi_open_session(), emi_submit_msg(), and open_send_connection(). 00622 {
00623 char *tmpbuff;
00624 int found = 0;
00625 int n;
00626 time_t start;
00627
00628 tmpbuff = gw_malloc(10 * 1024);
00629 memset(tmpbuff, 0, 10*1024);
00630 start = time(NULL);
00631 do {
00632 /* check for data */
00633 n = get_data(smsc, tmpbuff, 1024 * 10);
00634
00635 /* At least the X.31 interface wants to append the data.
00636 Kalle, what about the TCP/IP interface? Am I correct
00637 that you are assuming that the message arrives in a
00638 single read(2)? -mg */
00639 if (n > 0)
00640 memorybuffer_append_data(smsc, tmpbuff, n);
00641
00642 /* act on data */
00643 if (memorybuffer_has_rawmessage(smsc, op_type, 'R') > 0) {
00644 memorybuffer_cut_rawmessage(smsc, tmpbuff, 10*1024);
00645 debug("bb.sms.emi", 0, "Found ACK/NACK: <%s>", tmpbuff);
00646 found = 1;
00647 }
00648 } while (!found && ((time(NULL) - start) < 5));
00649
00650 gw_free(tmpbuff);
00651 return found;
00652 }
|
Here is the call graph for this function:
