summaryrefslogtreecommitdiffabout
path: root/gammu/emb/common/protocol/nokia/phonet.c
Side-by-side diff
Diffstat (limited to 'gammu/emb/common/protocol/nokia/phonet.c') (more/less context) (ignore whitespace changes)
-rw-r--r--gammu/emb/common/protocol/nokia/phonet.c217
1 files changed, 217 insertions, 0 deletions
diff --git a/gammu/emb/common/protocol/nokia/phonet.c b/gammu/emb/common/protocol/nokia/phonet.c
new file mode 100644
index 0000000..bc5717d
--- a/dev/null
+++ b/gammu/emb/common/protocol/nokia/phonet.c
@@ -0,0 +1,217 @@
+/* (c) 2002-2003 by Marcin Wiacek */
+/* based on some work from Gnokii */
+
+#include "../../gsmstate.h"
+
+#if defined(GSM_ENABLE_IRDA) || defined(GSM_ENABLE_PHONETBLUE) || defined(GSM_ENABLE_BLUEPHONET)
+
+#include <stdio.h>
+#include <string.h>
+
+#include "../../gsmcomon.h"
+#include "phonet.h"
+
+static GSM_Error PHONET_WriteMessage (GSM_StateMachine *s,
+ unsigned char *MsgBuffer,
+ int MsgLength,
+ unsigned char MsgType)
+{
+ unsigned char *buffer2;
+ int sent;
+
+ GSM_DumpMessageLevel3(s, MsgBuffer, MsgLength, MsgType);
+
+ buffer2 = (unsigned char *)malloc(MsgLength + 6);
+
+ buffer2[0] = PHONET_FRAME_ID,
+ buffer2[1] = PHONET_DEVICE_PHONE; //destination
+ buffer2[2] = PHONET_DEVICE_PC; //source
+
+ if (s->ConnectionType==GCT_PHONETBLUE || s->ConnectionType==GCT_BLUEPHONET) {
+ buffer2[0] = PHONET_BLUE_FRAME_ID;
+ buffer2[1] = PHONET_DEVICE_PHONE; //destination
+ buffer2[2] = PHONET_BLUE_DEVICE_PC; //source
+ }
+
+ buffer2[3] = MsgType;
+ buffer2[4] = MsgLength / 256;
+ buffer2[5] = MsgLength % 256;
+
+ memcpy(buffer2 + 6, MsgBuffer, MsgLength);
+
+ GSM_DumpMessageLevel2(s, buffer2+6, MsgLength, MsgType);
+
+ /* Sending to phone */
+ sent = s->Device.Functions->WriteDevice(s,buffer2,MsgLength+6);
+
+ free(buffer2);
+
+ if (sent!=MsgLength+6) return ERR_DEVICEWRITEERROR;
+ return ERR_NONE;
+}
+
+static GSM_Error PHONET_StateMachine(GSM_StateMachine *s, unsigned char rx_char)
+{
+ GSM_Protocol_PHONETData *d = &s->Protocol.Data.PHONET;
+ bool correct = false;
+
+ if (d->MsgRXState==RX_GetMessage) {
+ d->Msg.Buffer[d->Msg.Count] = rx_char;
+ d->Msg.Count++;
+
+ /* This is not last byte in frame */
+ if (d->Msg.Count != d->Msg.Length) return ERR_NONE;
+
+ s->Phone.Data.RequestMsg = &d->Msg;
+ s->Phone.Data.DispatchError = s->Phone.Functions->DispatchMessage(s);
+
+ free(d->Msg.Buffer);
+ d->Msg.Length = 0;
+ d->Msg.Buffer = NULL;
+
+ d->MsgRXState = RX_Sync;
+ return ERR_NONE;
+ }
+ if (d->MsgRXState==RX_GetLength2) {
+ d->Msg.Length = d->Msg.Length + rx_char;
+ d->Msg.Buffer = (unsigned char *)malloc(d->Msg.Length);
+
+ d->MsgRXState = RX_GetMessage;
+ return ERR_NONE;
+ }
+ if (d->MsgRXState==RX_GetLength1) {
+ d->Msg.Length = rx_char * 256;
+
+ d->MsgRXState = RX_GetLength2;
+ return ERR_NONE;
+ }
+ if (d->MsgRXState==RX_GetType) {
+ d->Msg.Type = rx_char;
+
+ d->MsgRXState = RX_GetLength1;
+ return ERR_NONE;
+ }
+ if (d->MsgRXState==RX_GetSource) {
+ if (rx_char != PHONET_DEVICE_PHONE) {
+ if (s->di.dl==DL_TEXT || s->di.dl==DL_TEXTALL || s->di.dl==DL_TEXTERROR ||
+ s->di.dl==DL_TEXTDATE || s->di.dl==DL_TEXTALLDATE || s->di.dl==DL_TEXTERRORDATE) {
+ smprintf(s,"[ERROR: incorrect char - %02x, not %02x]\n", rx_char, PHONET_DEVICE_PHONE);
+ }
+ d->MsgRXState = RX_Sync;
+ return ERR_NONE;
+ }
+ d->Msg.Source = rx_char;
+
+ d->MsgRXState = RX_GetType;
+ return ERR_NONE;
+ }
+ if (d->MsgRXState==RX_GetDestination) {
+ switch (s->ConnectionType) {
+ case GCT_IRDAPHONET:
+ if (rx_char == PHONET_DEVICE_PC) correct = true;
+ break;
+ case GCT_PHONETBLUE:
+ case GCT_BLUEPHONET:
+ if (rx_char == PHONET_BLUE_DEVICE_PC) correct = true;
+ break;
+ default:
+ break;
+ }
+ if (!correct) {
+ if (s->di.dl==DL_TEXT || s->di.dl==DL_TEXTALL || s->di.dl==DL_TEXTERROR ||
+ s->di.dl==DL_TEXTDATE || s->di.dl==DL_TEXTALLDATE || s->di.dl==DL_TEXTERRORDATE) {
+ smprintf(s,"[ERROR: incorrect char - %02x, not %02x]\n", rx_char, PHONET_DEVICE_PC);
+ }
+ d->MsgRXState = RX_Sync;
+ return ERR_NONE;
+ }
+ d->Msg.Destination = rx_char;
+
+ d->MsgRXState = RX_GetSource;
+ return ERR_NONE;
+ }
+ if (d->MsgRXState==RX_Sync) {
+ switch (s->ConnectionType) {
+ case GCT_IRDAPHONET:
+ if (rx_char == PHONET_FRAME_ID) correct = true;
+ break;
+ case GCT_PHONETBLUE:
+ case GCT_BLUEPHONET:
+ if (rx_char == PHONET_BLUE_FRAME_ID) correct = true;
+ break;
+ default:
+ break;
+ }
+ if (!correct) {
+ if (s->di.dl==DL_TEXT || s->di.dl==DL_TEXTALL || s->di.dl==DL_TEXTERROR ||
+ s->di.dl==DL_TEXTDATE || s->di.dl==DL_TEXTALLDATE || s->di.dl==DL_TEXTERRORDATE) {
+ smprintf(s,"[ERROR: incorrect char - %02x, not %02x]\n", rx_char, PHONET_FRAME_ID);
+ }
+ return ERR_NONE;
+ }
+ d->Msg.Count = 0;
+
+ d->MsgRXState = RX_GetDestination;
+ return ERR_NONE;
+ }
+ return ERR_NONE;
+}
+
+static GSM_Error PHONET_Initialise(GSM_StateMachine *s)
+{
+ int total = 0, i, n;
+ GSM_Protocol_PHONETData *d = &s->Protocol.Data.PHONET;
+ unsigned char req[50];
+
+ d->Msg.Length = 0;
+ d->Msg.Buffer = NULL;
+ d->MsgRXState = RX_Sync;
+
+ if (s->ConnectionType == GCT_PHONETBLUE || s->ConnectionType == GCT_BLUEPHONET) {
+ /* Send frame in PHONET style */
+ req[0] = PHONET_BLUE_FRAME_ID; req[1] = PHONET_DEVICE_PHONE;
+ req[2] = PHONET_BLUE_DEVICE_PC; req[3] = 0xD0;
+ req[4] = 0x00; req[5] = 0x01;
+ req[6] = 0x04;
+ if (s->Device.Functions->WriteDevice(s,req,7) != 7) return ERR_DEVICEWRITEERROR;
+
+ while (total < 7) {
+ n = s->Device.Functions->ReadDevice(s, req + total, 50 - total);
+ total += n;
+ }
+
+ /* Answer frame in PHONET style */
+ req[10] = PHONET_BLUE_FRAME_ID; req[11] = PHONET_BLUE_DEVICE_PC;
+ req[12] = PHONET_DEVICE_PHONE; req[13] = 0xD0;
+ req[14] = 0x00; req[15] = 0x01;
+ req[16] = 0x05;
+
+ for (i = 0; i < 7; i++) {
+ if (req[i] != req[10+i]) {
+ smprintf(s,"Incorrect byte in the answer\n");
+ return ERR_UNKNOWN;
+ }
+ }
+ }
+
+ return ERR_NONE;
+}
+
+static GSM_Error PHONET_Terminate(GSM_StateMachine *s)
+{
+ free(s->Protocol.Data.PHONET.Msg.Buffer);
+ return ERR_NONE;
+}
+
+GSM_Protocol_Functions PHONETProtocol = {
+ PHONET_WriteMessage,
+ PHONET_StateMachine,
+ PHONET_Initialise,
+ PHONET_Terminate
+};
+
+#endif
+
+/* How should editor hadle tabs in this file? Add editor commands here.
+ * vim: noexpandtab sw=8 ts=8 sts=8:
+ */