gboolean g_at_mux_setup_gsm0710(GAtChat *chat, GAtMuxSetupFunc notify, gpointer user_data, GDestroyNotify destroy) { struct mux_setup_data *msd; if (chat == NULL) return FALSE; if (notify == NULL) return FALSE; msd = g_new0(struct mux_setup_data, 1); msd->chat = g_at_chat_ref(chat); msd->func = notify; msd->user = user_data; msd->destroy = destroy; if (g_at_chat_send(chat, "AT+CMUX=?", cmux_prefix, mux_query_cb, msd, msd_free) > 0) return TRUE; if (msd) msd_free(msd); return FALSE; }
static int open_ip(void) { int sk, err; struct sockaddr_in addr; GAtSyntax *syntax; GIOChannel *channel; sk = socket(PF_INET, SOCK_STREAM, 0); if (sk < 0) return -EINVAL; memset(&addr, 0, sizeof(addr)); addr.sin_family = AF_INET; addr.sin_addr.s_addr = inet_addr(option_ip); addr.sin_port = htons(option_port); err = connect(sk, (struct sockaddr *) &addr, sizeof(addr)); if (err < 0) { close(sk); return err; } channel = g_io_channel_unix_new(sk); if (channel == NULL) { close(sk); return -ENOMEM; } syntax = g_at_syntax_new_gsmv1(); control = g_at_chat_new(channel, syntax); g_io_channel_unref(channel); g_at_syntax_unref(syntax); if (control == NULL) return -ENOMEM; g_at_chat_ref(control); modem = control; g_at_chat_set_debug(control, gsmdial_debug, ""); return 0; }
static int open_serial(void) { GAtSyntax *syntax; GIOChannel *channel; channel = g_at_tty_open(option_control, NULL); if (channel == NULL) return -EIO; syntax = g_at_syntax_new_gsm_permissive(); control = g_at_chat_new(channel, syntax); g_io_channel_unref(channel); g_at_syntax_unref(syntax); if (control == NULL) return -EIO; if (option_modem == NULL) { g_at_chat_ref(control); modem = control; g_at_chat_set_debug(control, gsmdial_debug, ""); } else { g_at_chat_set_debug(control, gsmdial_debug, "Control"); channel = g_at_tty_open(option_modem, NULL); if (channel == NULL) return -EIO; syntax = g_at_syntax_new_gsm_permissive(); modem = g_at_chat_new(channel, syntax); g_io_channel_unref(channel); g_at_syntax_unref(syntax); if (modem == NULL) return -EIO; g_at_chat_set_debug(modem, gsmdial_debug, "Modem"); } return 0; }
static void mux_query_cb(gboolean ok, GAtResult *result, gpointer user_data) { struct mux_setup_data *msd = user_data; struct mux_setup_data *nmsd; GAtResultIter iter; int min, max; int speed; char buf[64]; /* CMUX query not supported, abort */ if (!ok) goto error; g_at_result_iter_init(&iter, result); if (!g_at_result_iter_next(&iter, "+CMUX:")) goto error; /* Mode */ if (!g_at_result_iter_open_list(&iter)) goto error; if (!g_at_result_iter_next_range(&iter, &min, &max)) goto error; if (!g_at_result_iter_close_list(&iter)) goto error; if (min <= 1 && 1 <= max) msd->mode = 1; else if (min <= 0 && 0 <= max) msd->mode = 0; else goto error; /* Subset */ if (!g_at_result_iter_open_list(&iter)) goto error; if (!g_at_result_iter_next_range(&iter, &min, &max)) goto error; if (!g_at_result_iter_close_list(&iter)) goto error; if (min > 0) goto error; /* Speed, pick highest */ if (g_at_result_iter_open_list(&iter)) { if (!g_at_result_iter_next_range(&iter, &min, &max)) goto error; if (!g_at_result_iter_close_list(&iter)) goto error; speed = max; } else { if (!g_at_result_iter_skip_next(&iter)) goto error; /* not available/used */ speed = -1; } /* Frame size, pick defaults */ if (!g_at_result_iter_open_list(&iter)) goto error; if (!g_at_result_iter_next_range(&iter, &min, &max)) goto error; if (!g_at_result_iter_close_list(&iter)) goto error; if (msd->mode == 0) { if (min > 31 || max < 31) goto error; msd->frame_size = 31; } else if (msd->mode == 1) { if (min > 64 || max < 64) goto error; msd->frame_size = 64; } else goto error; nmsd = g_memdup(msd, sizeof(struct mux_setup_data)); g_at_chat_ref(nmsd->chat); if (speed < 0) sprintf(buf, "AT+CMUX=%u,0,,%u", msd->mode, msd->frame_size); else sprintf(buf, "AT+CMUX=%u,0,%u,%u", msd->mode, speed, msd->frame_size); if (g_at_chat_send(msd->chat, buf, none_prefix, mux_setup_cb, nmsd, msd_free) > 0) return; msd_free(nmsd); error: msd->func(NULL, msd->user); if (msd->destroy) msd->destroy(msd->user); }