Plugins may reference data structures allocated by each other.
They all need to be deinitialized first, only then it should be
safe to unload the libraries.
In case we try to enter the PIN/PUK and fail to enter a correct code,
the PIN/PUK retries are not rechecked as they should be.
Reported by: Florent Beillonnet <florent.beillonnet@gmail.com>
Typically responses to USSD requests are coming with status
zero (NOTIFY) but some are coming with status 2 (TERMINATED).
If those contain data, the data should be presented to the user.
If an operation is in progress and an operation is canceled, we don't
actually destroy it, but simply clear out the callback. In the case of
a context being destroyed, the operation is left on the simfs op_q with
a dangling pointer to the already freed context. So the current logic
in sim_fs_op_free tries to access invalid memory.
Fix this by performing the watch operations in sim_fs_end_current
instead and setting the context pointer appropriately.
0 0x00007ffff7b20517 in g_queue_is_empty () from /lib/x86_64-linux-gnu/libglib-2.0.so.0
1 0x00005555556adcdd in sim_fs_op_free (pointer=0x5555559cb990) at src/simfs.c:101
2 0x00007ffff7b205fc in g_queue_foreach () from /lib/x86_64-linux-gnu/libglib-2.0.so.0
3 0x00007ffff7b2065b in g_queue_free_full () from /lib/x86_64-linux-gnu/libglib-2.0.so.0
4 0x00005555556add81 in sim_fs_free (fs=0x5555559c0780) at src/simfs.c:125
5 0x00005555556828f3 in sim_remove (atom=0x5555559cb000) at src/sim.c:3175
6 0x000055555564f16f in flush_atoms (modem=0x555555a8fb00, new_state=MODEM_STATE_POWER_OFF) at src/modem.c:432
7 0x000055555564f3bd in modem_change_state (modem=0x555555a8fb00, new_state=MODEM_STATE_POWER_OFF)
at src/modem.c:510
8 0x000055555564ff99 in set_powered (modem=0x555555a8fb00, powered=0) at src/modem.c:896
9 0x000055555565074c in modem_set_property (conn=0x55555596c8d0, msg=0x55555596e460, data=0x555555a8fb00)
at src/modem.c:1120
==31530== 366 (48 direct, 318 indirect) bytes in 3 blocks are definitely lost in loss record 165 of 186
==31530== at 0x4C2BF8F: malloc (in /usr/lib64/valgrind/vgpreload_memcheck-amd64-linux.so)
==31530== by 0x50BB3A3: g_malloc (gmem.c:94)
==31530== by 0x50D62B4: g_slice_alloc (gslice.c:1025)
==31530== by 0x50D7A1E: g_slist_prepend (gslist.c:254)
==31530== by 0x4DD0B3: sim_parse_app_template_entries (simutil.c:1590)
==31530== by 0x4D2242: discover_apps_cb (sim.c:1509)
==31530== by 0x45E364: at_discover_apps_cb (sim.c:1579)
==31530== by 0x49CB5F: at_chat_finish_command (gatchat.c:459)
==31530== by 0x49DAC7: at_chat_handle_command_response (gatchat.c:521)
==31530== by 0x49DAC7: have_line (gatchat.c:600)
==31530== by 0x49DAC7: new_bytes (gatchat.c:759)
==31530== by 0x49FCEF: received_data (gatio.c:122)
==31530== by 0x510C2F3: g_io_unix_dispatch (giounix.c:165)
==31530== by 0x50B2D44: g_main_dispatch (gmain.c:3203)
==31530== 88 bytes in 2 blocks are definitely lost in loss record 132 of 186
==31530== at 0x4C2BF8F: malloc (in /usr/lib64/valgrind/vgpreload_memcheck-amd64-linux.so)
==31530== by 0x5847B97: vasprintf (in /lib64/libc-2.23.so)
==31530== by 0x510AE38: g_vasprintf (gprintf.c:316)
==31530== by 0x50D8BDF: g_strdup_vprintf (gstrfuncs.c:514)
==31530== by 0x50D8CAA: g_strdup_printf (gstrfuncs.c:540)
==31530== by 0x4F706B: build_nai (sim-auth.c:660)
==31530== by 0x4F706B: sim_auth_register (sim-auth.c:738)
==31530== by 0x4F706B: ofono_sim_auth_create (sim-auth.c:768)
==31530== by 0x4ACBB4: modem_change_state (modem.c:525)
==31530== by 0x4AD0CD: sim_state_watch.part.5 (modem.c:720)
==31530== by 0x4CF6D0: call_state_watches (sim.c:366)
==31530== by 0x4CF6D0: sim_set_ready (sim.c:1475)
==31530== by 0x4CF6D0: sim_imsi_obtained (sim.c:1577)
==31530== by 0x45D868: at_cimi_cb (sim.c:453)
==31530== by 0x49CB5F: at_chat_finish_command (gatchat.c:459)
==31530== by 0x49DAC7: at_chat_handle_command_response (gatchat.c:521)
==31530== by 0x49DAC7: have_line (gatchat.c:600)
==31530== by 0x49DAC7: new_bytes (gatchat.c:759)
aid_sessions was not properly reset to NULL when freed:
Program received signal SIGSEGV, Segmentation fault.
__ofono_watchlist_free (watchlist=0x0) at src/watch.c:91
91 for (l = watchlist->items; l; l = l->next) {
(gdb) bt
func=0x4ceca0 <aid_session_free>, user_data=0x0)
at /var/tmp/portage/dev-libs/glib-2.50.3-r1/work/glib-2.50.3/glib/gslist.c:878
free_func=0x4ceca0 <aid_session_free>)
at /var/tmp/portage/dev-libs/glib-2.50.3-r1/work/glib-2.50.3/glib/gslist.c:172
at src/sim.c:2605
user_data=<optimized out>) at plugins/phonesim.c:511
func=0x49c8a0 <at_notify_call_callback>, user_data=0x7fffffffdbc0)
at /var/tmp/portage/dev-libs/glib-2.50.3-r1/work/glib-2.50.3/glib/gslist.c:878
chat=0x7b70b0) at gatchat/gatchat.c:417
Calling from memory index is very similar in functionality to dialing
the last called number. So we rename the functions so we can reuse them,
to deal with memory index calling. Function names now also reflect this
is for hfp.
In addition to not doing unnecessary SIM I/O, this fixes memory leaks
like this one:
==10096== 74 (56 direct, 18 indirect) bytes in 2 blocks are definitely lost in loss record 1,252 of 1,342
==10096== at 0x4841BF0: calloc (vg_replace_malloc.c)
==10096== by 0x4B03117: g_malloc0 (gmem.c)
==10096== by 0xF83DF: concat_lang_prefs (sim.c)
==10096== by 0xF8697: sim_efpl_read_cb (sim.c)
==10096== by 0x12CBF7: sim_fs_op_read_block_cb (simfs.c)
Fix an error message from dbus about the path supplied not being valid.
Related to commit f58e7685b0
ofonod[19107]: src/voicecall.c:voicecall_dial_shortcut() check position
ofonod[19107]: src/voicecall.c:synthesize_outgoing_call() Registering new call: 1
process 19107: arguments to dbus_message_iter_append_basic() were incorrect, assertion "_dbus_check_is_valid_path (*string_p)" failed in file ../../../dbus/dbus-message.c line 2759.
This is normally a bug in some application using the D-Bus library.
Some protocols (like MBIM) do not properly support default bearer
semantics. Instead they want everything to function like UMTS/GSM where
the context has to be explicitly attached / activated.
This change is likely to break multiple drivers. One can easily emulate
the current behavior (pre-this commit) by calling
ofono_sim_initialized_notify after ofono_sim_inserted_notify.
All the functionality for the simauth driver was moved
into the sim atom. This patch transitions the simauth
atom to using those API's instead of the simauth driver
API's.
With this change it made more sense to store each AID
as its own object structure so the AID and object path
could be re-used rather than generating it on the fly.
Renamed the simauth 'sim' variable to 'sa' to keep it
consistent now that the simauth structure references
the sim atom as 'sim'.
API to create a sim context for the ISIM application, if found.
During AID discovery, if an ISIM AID is found, a new fs object is
initialized for the ISIM which will be used for any future
ISIM context creation.
The simfs atom could not read EF's that did not exist on the
'default' ADF directory. This implements a new way to read EF's
that exist on a given AID. A new fs object/context can be
initialized for a given AID. Using this fs context with
the existing read file API will read from that AID rather than
the default ADF.
Accessing an AID requires opening a channel to that application.
This patch implements session management API's so that other atoms
can access a given AID. Now any atom can get a session ID from the
sim atom. This will either reuse an existing session or open a new
channel. Once done, the atom should release the session which will
automatically close the channel when no atoms are using it.
The major functional change to the sim atom is the AID discovery
phase of initialization. Now, the sim atom is not 'ready' until AID
discovery finishes where before, the sim was 'ready' after the IMSI
had been obtained. If application discovery is not supported then
the the sim atom behaves as it did before.
The Le parameter in the AUTHENTICATE command was not being
set for GSM authentication. This did work, but explicitly
setting it to 0 as UMTS does was more consitent.
The state needs to be checked prior to calling __ofono_atom_register
because atom registration calls OFONO_ATOM_WATCH_CONDITION_REGISTERED
callbacks each of which may call ofono_sim_inserted_notify. Should
that happen, by the time __ofono_atom_register returns, ofono_sim
will be in OFONO_SIM_STATE_INSERTED state and sim_initialize will
be called twice if the initial state was OFONO_SIM_STATE_NOT_PRESENT.
If nothing else, that results in memory leaks like this one (because
IMSI will be queried twice, among other things):
==3017== 16 bytes in 1 blocks are definitely lost in loss record 187 of 475
==3017== at 0x483F380: malloc (vg_replace_malloc.c:296)
==3017== by 0x4AFB0DF: g_malloc (gmem.c:94)
==3017== by 0x4B12185: g_strdup (gstrfuncs.c:363)
==3017== by 0xF79D3: sim_imsi_obtained (sim.c:1535)
==3017== by 0xF7BB3: sim_imsi_cb (sim.c:1594)
==3017== by 0x66C23: at_cimi_cb (sim.c:441)
==3017== by 0xA6B53: at_chat_finish_command (gatchat.c:459)
==3017== by 0xA6D9F: at_chat_handle_command_response (gatchat.c:521)
==3017== by 0xA70AF: have_line (gatchat.c:600)
==3017== by 0xA76DF: new_bytes (gatchat.c:759)
==3017== by 0xABACF: received_data (gatio.c:122)
==3017== by 0xAD093: watch_dispatch (gatmux.c:461)
==3017== by 0xAC5D3: dispatch_sources (gatmux.c:180)
==3017== by 0xAC98F: received_data (gatmux.c:265)
==3017== by 0x4AF606F: g_main_dispatch (gmain.c:3154)
==3017== by 0x4AF606F: g_main_context_dispatch (gmain.c:3769)
==3017== by 0x4AF631D: g_main_context_iterate.isra.4 (gmain.c:3840)
==3017== by 0x4AF658F: g_main_loop_run (gmain.c:4034)
==3017== by 0xBE8AF: main (main.c:261)
synthethize_outgoing_call was only used once from dial_handle_result.
So move all the logic of registering the call to D-Bus and adding it to
the voicecalls list to that function.
This will allow synthethize_outgoing_call to be used from other
callbacks where the dial callback is guaranteed to return before any
call state notifications, e.g. in the case of +BLDN.
The sim-auth module atom can now be used for SIM application discovery
and authentication. The atom will automatically discover SIM
applications available on the SIM and register a new DBus object under
the modem, whos name is the AID string e.g.
/modem1/A0000000871004FFFFFFFF8906190000
A list of discovered AID object paths and types can be retrieved by
calling GetApplications() under the modems (new)
org.ofono.SimAuthentication interface which returns "a{oa{sv}}" where
o = path (e.g. above)
and the dictionary contains the following properties:
Type: "Umts" or "Ims"
Name: "USim" or "ISim"
The Type signifies which interfaces the AID object will have:
Umts = org.ofono.USimApplication
Ims = org.ofono.ISimApplication
These interfaces will contain the supported USIM/ISIM authentication
algorithms. Where:
org.ofono.USimApplication has:
GetProperties()
GsmAuthenticate()
UmtsAuthenticate()
org.ofono.ISimApplication has:
GetProperties()
ImsAuthenticate()
The existing service check API takes both SST and UST services
and could inadvertently return success on a service if one
(SST or UST) service did not exist. This adds an API specifically
for checking for a UST service, and if the UST dir is not available
it will return FALSE, rather than possibly returning true on some
other SST service.
Parsing a SIM application only copied the 16 byte AID
portion, which included the application type. Parsing out
the type makes sorting much easier for modules using the
parser.
call_status_to_string() is useful for debug output.
Change signature to contain enum call_status
Replace default case to get compiler warning when new enums added
... when a USSD notification is received. Some networks
send 0 (no further user action required) after the response
timeout expires. That should result in the user input form
getting removed from the ME screen.
Errors returned by g_key_file_get_integer have to be deallocated
by the caller to avoid leaks like these:
==13330== 104 (24 direct, 80 indirect) bytes in 2 blocks are definitely lost
==13330== at 0x483F3EC: malloc (vg_replace_malloc.c)
==13330== by 0x4B020DF: g_malloc (gmem.c)
==13330== by 0x4B17F51: g_slice_alloc (gslice.c)
==13330== by 0x4AE80B9: g_error_new_valist (gerror.c)
==13330== by 0x4AE830B: g_set_error (gerror.c)
==13330== by 0x4AF5681: g_key_file_get_value (gkeyfile.c)
==13330== by 0x4AF6817: g_key_file_get_integer (gkeyfile.c)
==13330== by 0x10CFE3: radio_load_settings (radio-settings.c)
==13330== by 0x10D2E3: ofono_radio_settings_register (radio-settings.c)
There are two problems with using pri_set_apn. The first issue is that
this function was built to be used by the set_property handler and
assumes the presence of a pending DBusMessage.
The second issue is that it touches the settings store.
In the case of auto-activated contexts no pending message exists. Also,
we should not be touching the settings store as the APN might
potentially be a value that has not been provisioned. Or in some cases
bogus.
This is a "leaf" header and doesn't even have header guards, but
it still seems natural that the header should pull in its own declarations
rather than relying on the including source file to ensure that they
are included.
The ofono_gprs_cid_activated attachment machinery cannot go through
ofono_gprs_status_notify for getting the attached property set because
that would result in the automatic contexts that were just set up
being released. As such, it needs to call gprs_set_attached_property
manually. Doing so, however, means that the driver_attached property
never gets set, resulting in all contexts being released when the
network transitions between registered states (roaming/non-roaming).
ofono_gprs_status_notify is an asynchronous notification that messes
with the 'attached' state of the GPRS atom. This method is normally
prevented from running while an attach is in progress because the
attachment machinery wants to finish up and make it's own determination
of attach state.
When automatic context activation is relevant, as for LTE networks,
the ofono_gprs_cid_activated machinery replaces the usual set_attach
machinery for attaching to the network. The cid_activated variant,
however, does not guard against simulatenous invocations of
ofono_gprs_status_notify. This causes a race whereby status_notify
sets the state to 'attached' before the context is fully constructed
and set to active. If the connection manager sees the 'attached'
state before there are any 'active' contexts, it may decide to
activate a context manually which is not the correct behaviour for
this type of network.
This patch makes the *_cid_activated machinery an 'attaching' state,
introducing the same guards that set_attached has to prevent
ofono_gprs_status_notify from running concurrently.
Calling set_online(TRUE) for an AlwaysOnline modem should succeed; the
modem is, after all, in the requested state when the call returns.
Returning not_implemented is not necessarily wrong, but it's a bit ugly.
SIM card can be removed while the query is in progress. There's
still a remote possibility that SIM card is removed and inserted
back while the query is pending, that would start the second query
sequence and end up invoking sim_initialize() twice. But at least
these checks reduce the probability of something like that happening.
Valgrind was complaining about it like this:
==18099== Conditional jump or move depends on uninitialised value(s)
==18099== at 0x4C32281: strspn
==18099== by 0x41286B: cbs_decode_text (smsutil.c:4140)
==18099== by 0x40675C: test_cbs_encode_decode (test-sms.c:1417)
Otherwise the attached state gets to be set before the actual LTE
automatic context is ready. This triggers a race between connman
and ofono: connman sees status attached before the context is active
so connman will try to activate another context with same apn and will
fail over and over again.
The spec supports UCS2, but in reality UTF-16 is used, which supports
4-byte characters, which could be split into different message
fragments. Accumulate the entire UTF-16 message before converting to
UTF8.
Author: Martin Jones <martin.jones@jolla.com>
This implementation can only get/set the default APN setting. But
anything expected for this atom is there:
* D-Bus interface
* sync-ing settings to/from file
* interaction with driver
... in pri_deactivate_callback
This prevents attached state from getting stuck at 0 like this:
1. Context deactivation is initiated over D-Bus, ctx->pending is set
2. Attached becomes FALSE, context is still marked as active
3. Attached becomes TRUE, gprs_attached_update sets GPRS_FLAG_ATTACHED_UPDATE
4. Deactivation completes, attached is 0, driver_attached is 1
Futher network status updates don't call gprs_attached_update because
driver_attached is still 1, so attached is staying 0 until we lose the
data registration again which may not happen for quite a long time.
query facility during initialization is modified from back
to back invocation to chain manner to keep it inline with
RIL design. All vendor RIL does not support back to back
handling since RIL telephony framework sends the request
synchronously.
The set_band method takes two parameters for band settings, one for gsm
and one for umts. When loaded from storage, and they are not set to
defaults, the band variables can get out of sync when setting the
GsmBand and UmtsBand properties.
After input PIN wrong 3 times, sim main state (include spn_watches)
is freed. but the watch id still be kept by other atoms (network and
gprs), when remove the atom, it will try to remove the watch from
spn_watches, ofono daemon will crash.
rs->imsi is only freed when rs->settings is true. So tweak the logic
inside radio_load_settings to only strdup the imsi when settings
creation has succeeded.
In some cases it is possible that a context is opened after a detach
event has been received, and right before an attach, depending on the
modem. We make sure that those contexts are removed to keep
consistency.