Hi Guillaume, > +static void request_reply(DBusPendingCall *call, void *user_data) > +{ > + struct pns_req *req = user_data; > + struct ofono_private_network_settings pns; > + DBusMessageIter array, dict, entry; > + DBusMessage *reply; > + const char *path; > + > + DBG(""); > + > + pns.fd = -1; > + pns.server_ip = NULL; > + pns.peer_ip = NULL; > + pns.primary_dns = NULL; > + pns.secondary_dns = NULL; > + > + req->pending = NULL; > + > + reply = dbus_pending_call_steal_reply(call); > + if (!reply) > + goto error; > + > + if (dbus_message_get_type(reply) == DBUS_MESSAGE_TYPE_ERROR) > + goto error; > + > + if (dbus_message_iter_init(reply, &array) == FALSE) > + goto error; > + > + if (dbus_message_iter_get_arg_type(&array) != DBUS_TYPE_OBJECT_PATH) > + goto error; > + > + dbus_message_iter_get_basic(&array, &path); > + > + dbus_message_iter_next(&array); > + if (dbus_message_iter_get_arg_type(&array) != DBUS_TYPE_ARRAY) > + goto error; > + > + if (req->redundant == TRUE) > + goto release; > + > + dbus_message_iter_recurse(&array, &dict); > + > + while (dbus_message_iter_get_arg_type(&dict) == DBUS_TYPE_DICT_ENTRY) { > + DBusMessageIter iter; > + const char *key; > + int type; > + > + dbus_message_iter_recurse(&dict, &entry); > + > + dbus_message_iter_get_basic(&entry, &key); > + > + dbus_message_iter_next(&entry); > + dbus_message_iter_recurse(&entry, &iter); > + > + type = dbus_message_iter_get_arg_type(&iter); > + if (type != DBUS_TYPE_STRING) > + break; > + > + if (g_str_equal(key, "ServerIPv4") && > + type == DBUS_TYPE_STRING) > + dbus_message_iter_get_basic(&iter, &pns.server_ip); > + else if (g_str_equal(key, "PeerIPv4") && > + type == DBUS_TYPE_STRING) > + dbus_message_iter_get_basic(&iter, &pns.peer_ip); > + else if (g_str_equal(key, "PrimaryDNS") && > + type == DBUS_TYPE_STRING) > + dbus_message_iter_get_basic(&iter, &pns.primary_dns); > + else if (g_str_equal(key, "SecondaryDNS") && > + type == DBUS_TYPE_STRING) > + dbus_message_iter_get_basic(&iter, &pns.secondary_dns); > + > + dbus_message_iter_next(&dict); > + } > + > + dbus_message_iter_next(&array); > + if (dbus_message_iter_get_arg_type(&array) != DBUS_TYPE_UNIX_FD) > + goto error; > + > + dbus_message_iter_get_basic(&array, &pns.fd); > + DBG("Fildescriptor = %d\n", pns.fd); > + > + req->path = g_strdup(path); > + DBG("Object path = %s\n", req->path); > + > + if (pns.server_ip == NULL || pns.peer_ip == NULL || > + pns.primary_dns == NULL || pns.secondary_dns == NULL || > + pns.fd < 0) { > + ofono_error("Error while reading dictionnary...\n"); > + goto release; > + } > + > + req->cb(&pns, req->data); > + > + dbus_message_unref(reply); > + dbus_pending_call_unref(call); > + > + return; > + > +release: > + pns_release(req->uid); > +error: > + if (pns.fd >= 0) > + close(pns.fd); > + > + if (req->redundant == FALSE) > + req->cb(NULL, req->data); And how do you think you will be using req->redundant when you just freed req in pns_release above? > + > + if (reply) > + dbus_message_unref(reply); > + > + dbus_pending_call_unref(call); > +} > + Anyhow, I applied this patch and refactored it very heavily afterward. Please test my changes, particularly the error conditions with an older version of ConnMan. If things are working nicely please send a patch marking the DUN emulator task as done. Regards, -Denis