예제 #1
0
static int read_msg(Msg **msg, Octstr *os, long *off)
{
    unsigned char buf[4];
    long i;
    Octstr *pack;

    gw_assert(*off >= 0);
    if (*off + 4 > octstr_len(os)) {
        error(0, "Packet too short while unpacking Msg.");
        return -1;
    }

    octstr_get_many_chars((char*)buf, os, *off, 4);
    i = decode_network_long(buf);
    *off  +=  4;
    
    pack = octstr_copy(os, *off, i);
    *off += octstr_len(pack);
    *msg = store_msg_unpack(pack);
    octstr_destroy(pack);
    
    if (!*msg)
        return -1;
    
    return 0;
}
예제 #2
0
파일: test_cimd2.c 프로젝트: armic/erpts
static void write_data(Octstr *out, int fd) {
	unsigned char buf[EVIL_BUFSIZE];
	int len;
	ssize_t ret;
	
	len = sizeof(buf);
	if (len > octstr_len(out))
		len = octstr_len(out);
	if (len == 0)
		return;
	octstr_get_many_chars(buf, out, 0, len);
	ret = write(fd, buf, len);
	if (ret > 0) {
		if (logging == LOG_data)
			pretty_print(buf, ret);
		octstr_delete(out, 0, ret);
	} else if (ret == 0) {
		warning(0, "empty write");
	} else {
		if (errno == EINTR || errno == EAGAIN)
			return;
		error(errno, "write_data");
		exit(1);
	}
}
예제 #3
0
파일: html.c 프로젝트: tphipps/kannel
/* Is there a comment beginning at offset `pos'? */
static int html_comment_begins(Octstr *html, long pos)
{
    char buf[10];

    octstr_get_many_chars(buf, html, pos, 4);
    buf[5] = '\0';
    return strcmp(buf, "<!--") == 0;
}
예제 #4
0
/*
 * Find the first packet in "in", delete it from "in", and return it as
 * a struct.  Return NULL if "in" contains no packet.  Always delete
 * leading non-packet data from "in".
 */
static struct packet *packet_extract(Octstr *in, SMSCConn *conn)
{
    Octstr *packet;
    int size, i;
    static char s[4][4] = {
        { 0x01, 0x0b, 0x00, 0x00 },
        { 0x01, 0x00, 0x00, 0x00 },
        { 0x00, 0x04, 0x00, 0x00 },
        { 0x00, 0x09, 0x00, 0x00 }
    }; /* msgtype, oper, 0, 0 */
    char known_bytes[4];

    if (octstr_len(in) < 10)
        return NULL;
    octstr_get_many_chars(known_bytes, in, 4, 4);
    /* Find s, and delete everything up to it. */
    /* If packet starts with one of s, it should be good packet */
    for (i = 0; i < 4; i++) {
        if (memcmp(s[i], known_bytes, 4) == 0)
            break;
    }

    if (i >= 4) {
        error(0, "OISD[%s]: wrong packet",
              octstr_get_cstr(conn->id));
        octstr_dump(in, 0);
        return NULL;
    }

    /* Find end of packet */
    size = (octstr_get_char(in, 9) << 8) | octstr_get_char(in, 8);

    if (size + 10 > octstr_len(in))
        return NULL;

    packet = octstr_copy(in, 0, size + 10);
    octstr_delete(in, 0, size + 10);

    return packet_parse(packet);
}
예제 #5
0
파일: smpp_pdu.c 프로젝트: armic/erpts
long smpp_pdu_read_len(Connection *conn)
{
    Octstr *os;
    char buf[4];    /* The length is 4 octets. */
    long len;

    os = conn_read_fixed(conn, sizeof(buf));
    if (os == NULL)
    	return 0;
    octstr_get_many_chars(buf, os, 0, sizeof(buf));
    octstr_destroy(os);
    len = decode_network_long(buf);
    if (len < MIN_SMPP_PDU_LEN) {
	error(0, "SMPP: PDU length was too small (%ld, minimum is %ld).",
	      len, (long) MIN_SMPP_PDU_LEN);
    	return -1;
    }
    if (len > MAX_SMPP_PDU_LEN) {
	error(0, "SMPP: PDU length was too large (%ld, maximum is %ld).",
	      len, (long) MAX_SMPP_PDU_LEN);
    	return -1;
    }
    return len;
}
예제 #6
0
파일: html.c 프로젝트: tphipps/kannel
/* Convert an HTML entity into a single character and advance `*html' past
   the entity. */
static void convert_html_entity(Octstr *sms, Octstr *html, long *pos)
{
    static struct {
        char *entity;
        int latin1;
    }
    tab[] = {
        { "&amp;", '&' },
        { "&lt;", '<' },
        { "&gt;", '>' },

        /* The following is copied from

        	http://www.hut.fi/~jkorpela/HTML3.2/latin1.html

           by Jukka Korpela. Hand and script edited to form this
           table. */

        { "&nbsp;", ' ' },
        { "&iexcl;", 161 },
        { "&cent;", 162 },
        { "&pound;", 163 },
        { "&curren;", 164 },
        { "&yen;", 165 },
        { "&brvbar;", 166 },
        { "&sect;", 167 },
        { "&uml;", 168 },
        { "&copy;", 169 },
        { "&ordf;", 170 },
        { "&laquo;", 171 },
        { "&not;", 172 },
        { "&shy;", 173 },
        { "&reg;", 174 },
        { "&macr;", 175 },
        { "&deg;", 176 },
        { "&plusmn;", 177 },
        { "&sup2;", 178 },
        { "&sup3;", 179 },
        { "&acute;", 180 },
        { "&micro;", 181 },
        { "&para;", 182 },
        { "&middot;", 183 },
        { "&cedil;", 184 },
        { "&sup1;", 185 },
        { "&ordm;", 186 },
        { "&raquo;", 187 },
        { "&frac14;", 188 },
        { "&frac12;", 189 },
        { "&frac34;", 190 },
        { "&iquest;", 191 },
        { "&Agrave;", 192 },
        { "&Aacute;", 193 },
        { "&Acirc;", 194 },
        { "&Atilde;", 195 },
        { "&Auml;", 196 },
        { "&Aring;", 197 },
        { "&AElig;", 198 },
        { "&Ccedil;", 199 },
        { "&Egrave;", 200 },
        { "&Eacute;", 201 },
        { "&Ecirc;", 202 },
        { "&Euml;", 203 },
        { "&Igrave;", 204 },
        { "&Iacute;", 205 },
        { "&Icirc;", 206 },
        { "&Iuml;", 207 },
        { "&ETH;", 208 },
        { "&Ntilde;", 209 },
        { "&Ograve;", 210 },
        { "&Oacute;", 211 },
        { "&Ocirc;", 212 },
        { "&Otilde;", 213 },
        { "&Ouml;", 214 },
        { "&times;", 215 },
        { "&Oslash;", 216 },
        { "&Ugrave;", 217 },
        { "&Uacute;", 218 },
        { "&Ucirc;", 219 },
        { "&Uuml;", 220 },
        { "&Yacute;", 221 },
        { "&THORN;", 222 },
        { "&szlig;", 223 },
        { "&agrave;", 224 },
        { "&aacute;", 225 },
        { "&acirc;", 226 },
        { "&atilde;", 227 },
        { "&auml;", 228 },
        { "&aring;", 229 },
        { "&aelig;", 230 },
        { "&ccedil;", 231 },
        { "&egrave;", 232 },
        { "&eacute;", 233 },
        { "&ecirc;", 234 },
        { "&euml;", 235 },
        { "&igrave;", 236 },
        { "&iacute;", 237 },
        { "&icirc;", 238 },
        { "&iuml;", 239 },
        { "&eth;", 240 },
        { "&ntilde;", 241 },
        { "&ograve;", 242 },
        { "&oacute;", 243 },
        { "&ocirc;", 244 },
        { "&otilde;", 245 },
        { "&ouml;", 246 },
        { "&divide;", 247 },
        { "&oslash;", 248 },
        { "&ugrave;", 249 },
        { "&uacute;", 250 },
        { "&ucirc;", 251 },
        { "&uuml;", 252 },
        { "&yacute;", 253 },
        { "&thorn;", 254 },
        { "&yuml;", 255 },
    };
    int num_tab = sizeof(tab) / sizeof(tab[0]);
    long i, code;
    size_t len;
    char buf[1024];

    if (octstr_get_char(html, *pos + 1) == '#') {
        if (octstr_get_char(html, *pos + 2) == 'x' || octstr_get_char(html, *pos + 2) == 'X')
            i = octstr_parse_long(&code, html, *pos + 3, 16); /* hex */
        else
            i = octstr_parse_long(&code, html, *pos + 2, 10); /* decimal */
        if (i > 0) {
            if (code < 256)
                octstr_append_char(sms, code);
            *pos = i + 1;
            if (octstr_get_char(html, *pos) == ';')
                ++(*pos);
        } else {
            ++(*pos);
            octstr_append_char(sms, '&');
        }
    } else {
        for (i = 0; i < num_tab; ++i) {
            len = strlen(tab[i].entity);
            octstr_get_many_chars(buf, html, *pos, len);
            buf[len] = '\0';
            if (strcmp(buf, tab[i].entity) == 0) {
                *pos += len;
                octstr_append_char(sms, tab[i].latin1);
                break;
            }
        }
        if (i == num_tab) {
            ++(*pos);
            octstr_append_char(sms, '&');
        }
    }
}
예제 #7
0
파일: conn.c 프로젝트: pwhelan/kannel
Octstr *conn_read_withlen(Connection *conn)
{
    Octstr *result = NULL;
    unsigned char lengthbuf[4];
    long length = 0; /* for compiler please */
    int try, retry;

    lock_in(conn);

    for (try = 1; try <= 2; try++) {
        if (try > 1)
            unlocked_read(conn);

        do {
            retry = 0;
            /* First get the length. */
            if (unlocked_inbuf_len(conn) < 4)
                continue;

            octstr_get_many_chars(lengthbuf, conn->inbuf, conn->inbufpos, 4);
            length = decode_network_long(lengthbuf);

            if (length < 0) {
                warning(0, "conn_read_withlen: got negative length, skipping");
                conn->inbufpos += 4;
                retry = 1;
             }
        } while(retry == 1);

        /* Then get the data. */
        if (unlocked_inbuf_len(conn) - 4 < length)
            continue;

        conn->inbufpos += 4;
        result = unlocked_get(conn, length);
        gw_claim_area(result);
        break;
    }

    unlock_in(conn);
    return result;
}

Octstr *conn_read_packet(Connection *conn, int startmark, int endmark)
{
    int startpos, endpos;
    Octstr *result = NULL;
    int try;

    lock_in(conn);

    for (try = 1; try <= 2; try++) {
        if (try > 1)
            unlocked_read(conn);

        /* Find startmark, and discard everything up to it */
        if (startmark >= 0) {
            startpos = octstr_search_char(conn->inbuf, startmark, conn->inbufpos);
            if (startpos < 0) {
                conn->inbufpos = octstr_len(conn->inbuf);
                continue;
            } else {
                conn->inbufpos = startpos;
            }
        } else {
           startpos = conn->inbufpos;
        }

        /* Find first endmark after startmark */
        endpos = octstr_search_char(conn->inbuf, endmark, conn->inbufpos);
        if (endpos < 0)
            continue;

        result = unlocked_get(conn, endpos - startpos + 1);
        gw_claim_area(result);
        break;
    }

    unlock_in(conn);
    return result;
}

#ifdef HAVE_LIBSSL
X509 *conn_get_peer_certificate(Connection *conn) 
{
    /* Don't know if it needed to be locked , but better safe as crash */
    lock_out(conn);
    lock_in(conn);
    if (conn->peer_certificate == NULL && conn->ssl != NULL)
        conn->peer_certificate = SSL_get_peer_certificate(conn->ssl);
    unlock_in(conn);
    unlock_out(conn);
    
    return conn->peer_certificate;
}

/*
 * XXX Alex decalred the RSA callback routine static and now we're getting 
 * warning messages for our automatic compilation tests. So we are commenting
 * the function out to avoid the warnings.
 *

static RSA *tmp_rsa_callback(SSL *ssl, int export, int key_len)
{
    static RSA *rsa = NULL;
    debug("gwlib.http", 0, "SSL: Generating new RSA key (export=%d, keylen=%d)", export, key_len);
    if (export) {
	   rsa = RSA_generate_key(key_len, RSA_F4, NULL, NULL);
    } else {
	   debug("gwlib.http", 0, "SSL: Export not set");
    }
    return rsa;
}
*/

static Mutex **ssl_static_locks = NULL;

/* the call-back function for the openssl crypto thread locking */
static void openssl_locking_function(int mode, int n, const char *file, int line)
{
    if (mode & CRYPTO_LOCK)
        mutex_lock(ssl_static_locks[n-1]);
    else
        mutex_unlock(ssl_static_locks[n-1]);
}

void openssl_init_locks(void)
{
    int c, maxlocks = CRYPTO_num_locks();

    gw_assert(ssl_static_locks == NULL);

    ssl_static_locks = gw_malloc(sizeof(Mutex *) * maxlocks);
    for (c = 0; c < maxlocks; c++)
        ssl_static_locks[c] = mutex_create();

    /* after the mutexes have been created, apply the call-back to it */
    CRYPTO_set_locking_callback(openssl_locking_function);
    CRYPTO_set_id_callback((CRYPTO_CALLBACK_PTR)gwthread_self);
}
예제 #8
0
/******************************************************************************
* Send a MT message, returns as in smsc_submit_smsmessage in smsc.h
*/
int cimd_submit_msg(SMSCenter *smsc, Msg *msg)
{

    char *tmpbuff = NULL, *tmptext = NULL;
    char msgtext[1024];
    int ret;
    int cmd = 0, err = 0;

    /* Fix these by implementing a could-not-send-because-
       protocol-does-not-allow in smsc.c or smsgateway.c */
    if (octstr_len(msg->sms.msgdata) + octstr_len(msg->sms.udhdata) < 1) {
	if (msg->sms.msgdata == NULL)
	    msg->sms.msgdata = octstr_create("");
	octstr_append_from_hex(msg->sms.msgdata, "20");
    }
    if (octstr_len(msg->sms.sender) < 1) {
        warning(0, "cimd_submit_smsmessage: ignoring message with 0-length field");
        goto okay;  /* THIS IS NOT OKAY!!!! XXX */
    }
    if (octstr_len(msg->sms.receiver) < 1) {
        warning(0, "cimd_submit_smsmessage: ignoring message with 0-length field");
        goto okay;  /* THIS IS NOT OKAY!!!! XXX */
    }

    tmpbuff = gw_malloc(10 * 1024);
    tmptext = gw_malloc(10 * 1024);

    memset(tmpbuff, 0, 10*1024);
    memset(tmptext, 0, 10*1024);
    memset(msgtext, 0, sizeof(msgtext));

    if (octstr_len(msg->sms.udhdata)) {
        octstr_get_many_chars(msgtext, msg->sms.udhdata, 0, octstr_len(msg->sms.udhdata));
        octstr_get_many_chars(msgtext + octstr_len(msg->sms.udhdata),
                              msg->sms.msgdata, 0,
                              140 - octstr_len(msg->sms.udhdata));
    } else {
        octstr_get_many_chars(msgtext, msg->sms.msgdata, 0,
                              octstr_len(msg->sms.msgdata));
    }

    /* XXX parse_iso88591_to_cimd should use Octstr
     * directly, or get a char* and a length, instead of using NUL
     * terminated strings.
     */
    parse_iso88591_to_cimd(msgtext, tmptext, 10*1024, smsc->alt_charset);

    /* If messages has UDHs, add the magic number 31 to the right spot */
    sprintf(tmpbuff, "%c%s%c%s%c%s%c%s%c%s%c%s%c%s%c%c",
            0x02,
            "03", 0x09,
            octstr_get_cstr(msg->sms.receiver), 0x09,
            tmptext, 0x09,
            "", 0x09,
            "", 0x09,
            (octstr_len(msg->sms.udhdata)) ? "31" : "", 0x09,
            "11", 0x03, 0x0A);

    ret = write_to_socket(smsc->socket, tmpbuff);
    if (ret < 0) {
        debug("bb.sms.cimd", 0, "cimd_submit_smsmessage: socket write error");
        goto error;
    }

    /* The Nokia SMSC MAY be configured to send delivery
       information, which we then will HAVE to acknowledge.
       Naturally the CIMD 1.3 protocol does not include any
       kind of negotiation mechanism. */
    ret = expect_acknowledge(smsc, &cmd, &err);

    if (ret >= 1) {

        if (cmd == 4) {
            send_acknowledge(smsc);
            goto okay;
        } else if (cmd == 3) {
            goto okay;
        }

    } else if (ret == 0) {

        if (cmd == 4) {
            send_acknowledge(smsc);
            goto okay;  /* FIXME XXX THIS IS BOGUS, FIX SMSGATEWAY.C */
            goto error;
        } else if (cmd == 3) {
            goto okay;  /* FIXME XXX THIS IS BOGUS, FIX SMSGATEWAY.C */
            goto error;
        } else {
            error(0, "Unexpected behaviour from the CIMD server");
            debug("bb.sms.cimd", 0, "cimd_submit_smsmessage: acknowledge was <%i>", ret);
            debug("bb.sms.cimd", 0, "cimd_submit_smsmessage: buffer==<%s>", smsc->buffer);
            goto error;
        }

    }

okay:
    gw_free(tmpbuff);
    gw_free(tmptext);
    return 0;

error:
    debug("bb.sms.cimd", 0, "cimd_submit_smsmessage: returning error");
    gw_free(tmpbuff);
    gw_free(tmptext);
    return -1;

}