From: Nils Faerber Date: Mon, 29 Aug 2011 09:37:02 +0000 (+0200) Subject: Implement streaming protocol (mw_feed_...) X-Git-Url: https://git.kernelconcepts.de/?p=metawatch.git;a=commitdiff_plain;h=7d8f5f3b7240d9d6418fd92f851ce903aaa49bf0 Implement streaming protocol (mw_feed_...) --- diff --git a/metawatch.c b/metawatch.c index 5c5b73b..4576d9f 100644 --- a/metawatch.c +++ b/metawatch.c @@ -480,7 +480,7 @@ void mw_set_status_change_event_cb(mwdevice_t *mwdevice, void (*mw_status_change * Protocol handling * ---------------------------------------------------------------------- */ -int decode_frame(mwdevice_t *mwdevice, unsigned char *buf, int len) +int mw_decode_frame(mwdevice_t *mwdevice, unsigned char *buf, int len) { unsigned short crc; unsigned char msglen; @@ -547,6 +547,38 @@ int decode_frame(mwdevice_t *mwdevice, unsigned char *buf, int len) } +int mw_feed_msg_buffer(mwdevice_t *mwdevice, unsigned char *buf, int len) +{ + char msgbuf[64]; + int tlen; + + if (len <= 0) + return -1; + + memcpy((mwdevice->pbuf+mwdevice->pbuf_len), buf, len); + mwdevice->pbuf_len += len; + + while (mwdevice->pbuf_len > 0) { + /* scan for MW_SOF */ + while (mwdevice->pbuf[0] != MW_SOF) { + memmove(mwdevice->pbuf, (mwdevice->pbuf+1), --mwdevice->pbuf_len); + } + tlen = mwdevice->pbuf[1]; + /* OK, there is an SOF but the message is too short */ + if (tlen > mwdevice->pbuf_len) { + /* we have to wait for more data to come in */ + break; + } + /* here we have a complete msg */ + memcpy(msgbuf, mwdevice->pbuf, tlen); + mw_decode_frame(mwdevice, msgbuf, tlen); + memmove(mwdevice->pbuf, (mwdevice->pbuf+tlen), tlen); + mwdevice->pbuf_len -= tlen; + } + return 0; +} + + /* ---------------------------------------------------------------------- * General code usage * ---------------------------------------------------------------------- */ @@ -555,6 +587,8 @@ int mw_init(mwdevice_t *mwdevice, int mw_fd) { memset(mwdevice, 0, sizeof(mwdevice_t)); mwdevice->mw_fd = mw_fd; + memset(mwdevice->pbuf, 0, MW_PBUF_LEN); + mwdevice->pbuf_len = 0; /* figure out which device we run with */ mw_send_frame(mwdevice, MW_GET_DEVICE_TYPE, 0, NULL, 0); diff --git a/metawatch.h b/metawatch.h index 5df07a0..4fbbc9b 100644 --- a/metawatch.h +++ b/metawatch.h @@ -10,8 +10,12 @@ #include #include "metawatch_protocol.h" +#define MW_PBUF_LEN 512 + typedef struct _mwdevice_t { int mw_fd; /* file decriptor for MW connection */ + char pbuf[MW_PBUF_LEN]; /* protocol receive buffer */ + int pbuf_len; unsigned char devtype; /* the device type of the connected device */ /* watch message callbacks */ void (*mw_get_device_type_response_cb) (struct _mwdevice_t *mwdevice, unsigned char devtype, void *user_data); @@ -79,7 +83,9 @@ int mw_disable_button(mwdevice_t *mwdevice, unsigned char mode, unsigned char bu int mw_advance_watch_hands(mwdevice_t *mwdevice, unsigned char hours, unsigned char minutes, unsigned char seconds); -int decode_frame(mwdevice_t *mwdevice, unsigned char *buf, int len); +int mw_decode_frame(mwdevice_t *mwdevice, unsigned char *buf, int len); + +int mw_feed_msg_buffer(mwdevice_t *mwdevice, unsigned char *buf, int len); int mw_init(mwdevice_t *mwdevice, int mw_fd); diff --git a/mw_main.c b/mw_main.c index dd4e4a4..a5c1083 100644 --- a/mw_main.c +++ b/mw_main.c @@ -448,7 +448,7 @@ gboolean handle_mw_io(GIOChannel *mw_io, GIOCondition condition, gpointer udata) mwdata_t *mdata = (mwdata_t *)udata; int rcvd; - rcvd = read(mdata->mwdevice.mw_fd, mdata->rcvbuf+mdata->rcvbuf_pos, 64); + rcvd = read(mdata->mwdevice.mw_fd, mdata->rcvbuf, 64); #ifdef DEBUG fprintf(stderr, "read %d bytes:\n", rcvd); #endif @@ -456,8 +456,7 @@ gboolean handle_mw_io(GIOChannel *mw_io, GIOCondition condition, gpointer udata) #ifdef DEBUG dump_frame(mdata->rcvbuf, rcvd); #endif - decode_frame(&mdata->mwdevice, mdata->rcvbuf, rcvd); - mdata->rcvbuf_pos = 0; + mw_feed_msg_buffer(&mdata->mwdevice, mdata->rcvbuf, rcvd); } return TRUE;