Compare commits

...

81 Commits

Author SHA1 Message Date
Slava Monich
6dddf527d5 Merge pull request #7 from monich/double-free
Fix double-free
2021-09-14 17:01:57 +03:00
Slava Monich
a9de07c2bb [ril] Fix double-free. JB#55547 2021-09-14 16:43:36 +03:00
Slava Monich
ecf14f5165 Merge pull request #4 from monich/ril-split
Make more APIs available to external plugins
2021-09-13 17:51:42 +03:00
Slava Monich
bc4c860a86 [ofono] Make more APIs available to external plugins. JB#55027
This allows to build Jolla ril driver as an external dynamically
loadable plugin.
2021-09-13 16:32:33 +03:00
Slava Monich
7684dd4295 Housekeeping 2021-09-13 14:32:44 +03:00
Slava Monich
f24a5be4ec Update upstream hash 2021-09-13 14:32:23 +03:00
Slava Monich
c45e207f12 Merge pull request #6 from PsychoGame/ofono-new
[ofono] Update baseline to 1.24. JB#54354
2021-09-13 14:26:53 +03:00
Marcel Holtmann
005f36bb89 Release 1.24 2021-09-07 21:48:50 +02:00
Marcel Holtmann
3d01485a05 gatchat: Use pragma to mask unknown pragma diagnostic options
gatchat/gatmux.c:33:32: error: unknown option after ‘#pragma GCC diagnostic’ kind [-Werror=pragmas]
 #pragma GCC diagnostic ignored "-Wcast-function-type"
                                ^~~~~~~~~~~~~~~~~~~~~~
2021-09-07 21:43:31 +02:00
Marcel Holtmann
cc7b30414f rilmodem: Use pragma to mask restrict buffer warnings
In file included from drivers/rilmodem/network-registration.c:40:
drivers/rilmodem/network-registration.c: In function ‘ril_cops_list_cb’:
./gril/gril.h:98:11: error: passing argument 1 to restrict-qualified parameter aliases with argument 3 [-Werror=restrict]
   sprintf(print_buf, x);  \
           ^~~~~~~~~
drivers/rilmodem/network-registration.c:583:3: note: in expansion of macro ‘g_ril_append_print_buf’
   g_ril_append_print_buf(nd->ril, "%s [lalpha=%s, salpha=%s, "
   ^~~~~~~~~~~~~~~~~~~~~~
./gril/gril.h:98:11: error: passing argument 1 to restrict-qualified parameter aliases with argument 3 [-Werror=restrict]
   sprintf(print_buf, x);  \
           ^~~~~~~~~
drivers/rilmodem/network-registration.c:593:2: note: in expansion of macro ‘g_ril_append_print_buf’
  g_ril_append_print_buf(nd->ril, "%s}", print_buf);
  ^~~~~~~~~~~~~~~~~~~~~~

In file included from drivers/rilmodem/call-forwarding.c:41:
drivers/rilmodem/call-forwarding.c: In function ‘ril_query_call_fwd_cb’:
./gril/gril.h:98:11: error: passing argument 1 to restrict-qualified parameter aliases with argument 3 [-Werror=restrict]
   sprintf(print_buf, x);  \
           ^~~~~~~~~
drivers/rilmodem/call-forwarding.c:114:3: note: in expansion of macro ‘g_ril_append_print_buf’
   g_ril_append_print_buf(fd->ril, "%s [%d,%d,%d,%s,%d]",
   ^~~~~~~~~~~~~~~~~~~~~~
./gril/gril.h:98:11: error: passing argument 1 to restrict-qualified parameter aliases with argument 3 [-Werror=restrict]
   sprintf(print_buf, x);  \
           ^~~~~~~~~
drivers/rilmodem/call-forwarding.c:124:2: note: in expansion of macro ‘g_ril_append_print_buf’
  g_ril_append_print_buf(fd->ril, "%s}", print_buf);
  ^~~~~~~~~~~~~~~~~~~~~~
2021-09-07 21:42:45 +02:00
Marcel Holtmann
1617b325de gatchat: Use pragma to mask GFunc casting warning
gatchat/gatmux.c: In function ‘watch_dispatch’:
gatchat/gatmux.c:454:17: error: cast between incompatible function types from ‘GSourceFunc’ {aka ‘int (*)(void *)’} to ‘gboolean (*)(GIOChannel *, GIOCondition,  void *)’ {aka ‘int (*)(struct _GIOChannel *, enum <anonymous>,  void *)’} [-Werror=cast-function-type]
  GIOFunc func = (GIOFunc) callback;
                 ^
2021-09-07 21:42:01 +02:00
Antara Borwankar
a8838c2287 atmodem: Support ETWS & CMAS on XMM series modems 2021-09-07 21:40:49 +02:00
Denis Kenzior
c8cd552851 sim: Fix not updating sim pin state
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>
2021-09-07 21:39:55 +02:00
Denis Kenzior
6995d8c42c AUTHORS: Mention Florent's contributions 2021-09-07 21:38:21 +02:00
Florent Beillonnet
17052d41de atmodem: Fix at_pin_send_puk userdata use
It seems that the function at_pin_send_puk should have been changed
along with at_pin_send, because it's also refering to the
at_pin_send_cb callback

See this commit : ba9f126716db3ae0bf6a3139088d9657cfb8b851
2021-09-07 21:37:38 +02:00
Denis Kenzior
70a93dcc5b gemalto: Whitespace fixes 2021-09-07 21:36:40 +02:00
Denis Kenzior
e3ea3abaa0 AUTHORS: Mention Varun's contributions 2021-09-07 21:36:00 +02:00
Varun Gargi
f60c44b034 udevng: remove vendor ID to make it generic for intel modem 2021-09-07 21:35:00 +02:00
James Prestwood
a679258b4a plugins: fixed crash in udevng
The return value from ofono_modem_register was not being checked. If this fails
the modem object is not setup and causes a crash. This was specifically seen
when using the mbim driver without having configured with mbim support.

Now the modem object gets destroyed properly if the modem registration fails.
2021-09-07 21:33:59 +02:00
Bob Ham
0ed72bcffa sim7100: Specify vendor ID while creating voicecall driver
This enables the atmodem voicecall driver to handle SIMCom quirks like
not setting AT+COLP=1.
2021-09-07 21:30:55 +02:00
Bob Ham
7d5a660604 atmodem: Don't set AT+COLP=1 on SIMCom modems
On the SIMCom SIM7100E, setting AT+COLP=1 causes there to be no
response at all from "ATD...;" commands until the call is answered.
The results in oFono stalling rather than creating a new VoiceCall
object.

We fix this by adding SIMCOM to the list of vendors for whom we set
AT+COLP=0 rather than AT+COLP=1.
2021-09-07 21:30:08 +02:00
Denis Kenzior
d67240c717 AUTHORS: Mention Bob's contributions 2021-09-07 21:26:39 +02:00
Bob Ham
b12016eb45 plugins: Add support for SIM7100E by SIMCom
Add support for the SIM7100E modem.  We add a new "sim7100" plugin
because there's no other AT-based modem that has support for both GPRS
and voice calls.
2021-09-07 21:25:40 +02:00
Denis Kenzior
bfec98afdf unit: Fix gcc warning
In file included from unit/test-mbim.c:28:0:
unit/test-mbim.c: In function ‘parse_device_caps’:
unit/test-mbim.c:332:9: error: suggest parentheses around assignment used as truth value [-Werror=parentheses]
  assert(cellular_class = 1);
2021-09-07 21:14:10 +02:00
Mark van der Putten
7376781211 gemalto: signal sim initialized
Modem type PLS8-E, firmware 03.017
2021-09-07 21:11:23 +02:00
Christophe Ronco
732160519a qmi: report SIM not inserted when unable to get PIN type 2021-09-07 21:08:55 +02:00
Christophe Ronco
f71d2a2b70 qmi: report failure or retry in case of invalid pin type
QMI_UIM_GET_CARD_STATUS is retried in more error cases
when trying to get password type.
In case of failure, driver report an error instead of
OFONO_SIM_PASSWORD_INVALID. This avoids a crash.
2021-09-07 21:08:08 +02:00
Christophe Ronco
793e9fcae4 qmi: use right slot and application during SIM detection
Use right slot and application to get card status, PIN status and PIN
retries. Without this patch, SIMs where selected application and slot
numbers are different are not detected.
2021-09-07 21:07:08 +02:00
Jonas Bonn
ae204ebf82 qmi: make services always shared 2021-09-07 21:05:05 +02:00
Jonas Bonn
30b09b35af gobi: Update to the new version_list changes 2021-09-07 21:03:54 +02:00
Jonas Bonn
1495f222b0 qmi: make version_list private 2021-09-07 21:02:38 +02:00
Jonas Bonn
b9b2765b21 qmi: assume version_list is up to date
The way things are currently coded, the gobi plugin calls
qmi_device_discover and does nothing else until it succeeds.  As such,
we can safely assume that the version_list is set up when we go to
create a service.
2021-09-07 20:59:42 +02:00
Jonas Bonn
29ecf1a59a qmi: drop header output parameter from request_alloc
The only thing this output parameter is being used for now is for
getting the transaction ID.  Return the TID directly from
__submit_requesta and drop the 'head' parameter altogether.
2021-09-07 20:58:52 +02:00
Jonas Bonn
f1d3367e0a qmi: request_alloc has no meaningful failure path
The only way request_alloc can fail is if one of the memory allocation
routines fail to allocate memory.  However, Linux memory allocation
doesn't really fail in this manner; memory can be overcommited and the
out-of-memory reaper will take care of re-establishing the balance when
excess memory is actually accessed.

Given this, request_alloc will never return anything other than success
and the failure paths will never be exercised.
2021-09-07 20:58:07 +02:00
Jonas Bonn
7131403177 qmi: unify common request header setup
The service and control requests differ slightly in their headers, but
this difference is minor enough that we can handle it directly in the
request submission routine.  This patch unifies the header setup for the
two request types.
2021-09-07 20:54:58 +02:00
Jonas Bonn
ff99f16ccb qmi: remove headroom parameter from req_alloc
The headroom can be established from the service type, so it's redundant
to pass it as a parameter.
2021-09-07 20:54:12 +02:00
Jonas Bonn
ccec9504a5 qmi: remove unused fields of service_send_data
After setting up the request structure, qmi_service_send makes no
further use of the 'param' and 'service' fields of the service_send_data
structure.  This patch removes those fields and frees 'param'
immediately after the request has been allocated and the parameter data
thereby copied into the send buffer.
2021-09-07 20:52:21 +02:00
Bassem Boubaker
e37ca6d384 gemalto: Clarify supported modem family name
Some gemalto modem family share almost the same base except some very
specific AT command and some hardware changes like ALSx and PXSx family
2021-09-07 20:49:34 +02:00
Mariem Cherif
ab5b76d6cf gemalto: handle sim is inserted or removed URCs 2021-09-07 20:48:14 +02:00
Denis Kenzior
35ef8fb8a1 qmi: Fix uninitialized value use
==2870== Conditional jump or move depends on uninitialised value(s)
==2870==    at 0x4C2ED31: __memcmp_sse4_1 (vg_replace_strmem.c:972)
==2870==    by 0x4F451A: sim_pin_retries_query_cb (sim.c:462)
==2870==    by 0x459BDD: query_pin_retries_cb (sim.c:544)
==2870==    by 0x45544A: service_send_callback (qmi.c:2143)
==2870==    by 0x452D00: handle_packet (qmi.c:815)
==2870==    by 0x452E85: received_data (qmi.c:863)
==2870==    by 0x508DB6C: g_main_context_dispatch (in /lib/x86_64-linux-gnu/libglib-2.0.so.0.4200.1)
==2870==    by 0x508DF47: ??? (in /lib/x86_64-linux-gnu/libglib-2.0.so.0.4200.1)
==2870==    by 0x508E271: g_main_loop_run (in /lib/x86_64-linux-gnu/libglib-2.0.so.0.4200.1)
==2870==    by 0x4C680B: main (main.c:256)
==2870==  Uninitialised value was created by a stack allocation
==2870==    at 0x459B1A: query_pin_retries_cb (sim.c:531)
==2870==
==2870== Conditional jump or move depends on uninitialised value(s)
==2870==    at 0x4F451D: sim_pin_retries_query_cb (sim.c:462)
==2870==    by 0x459BDD: query_pin_retries_cb (sim.c:544)
==2870==    by 0x45544A: service_send_callback (qmi.c:2143)
==2870==    by 0x452D00: handle_packet (qmi.c:815)
==2870==    by 0x452E85: received_data (qmi.c:863)
==2870==    by 0x508DB6C: g_main_context_dispatch (in /lib/x86_64-linux-gnu/libglib-2.0.so.0.4200.1)
==2870==    by 0x508DF47: ??? (in /lib/x86_64-linux-gnu/libglib-2.0.so.0.4200.1)
==2870==    by 0x508E271: g_main_loop_run (in /lib/x86_64-linux-gnu/libglib-2.0.so.0.4200.1)
==2870==    by 0x4C680B: main (main.c:256)
==2870==  Uninitialised value was created by a stack allocation
==2870==    at 0x459B1A: query_pin_retries_cb (sim.c:531)
==2870==
==2870== Conditional jump or move depends on uninitialised value(s)
==2870==    at 0x4F3DFB: get_pin_retries (sim.c:278)
==2870==    by 0x4F4553: sim_pin_retries_query_cb (sim.c:467)
==2870==    by 0x459BDD: query_pin_retries_cb (sim.c:544)
==2870==    by 0x45544A: service_send_callback (qmi.c:2143)
==2870==    by 0x452D00: handle_packet (qmi.c:815)
==2870==    by 0x452E85: received_data (qmi.c:863)
==2870==    by 0x508DB6C: g_main_context_dispatch (in /lib/x86_64-linux-gnu/libglib-2.0.so.0.4200.1)
==2870==    by 0x508DF47: ??? (in /lib/x86_64-linux-gnu/libglib-2.0.so.0.4200.1)
==2870==    by 0x508E271: g_main_loop_run (in /lib/x86_64-linux-gnu/libglib-2.0.so.0.4200.1)
==2870==    by 0x4C680B: main (main.c:256)
==2870==  Uninitialised value was created by a stack allocation
==2870==    at 0x459B1A: query_pin_retries_cb (sim.c:531)
==2870==
==2870== Conditional jump or move depends on uninitialised value(s)
==2870==    at 0x4F3E65: get_pin_retries (sim.c:288)
==2870==    by 0x4F4553: sim_pin_retries_query_cb (sim.c:467)
==2870==    by 0x459BDD: query_pin_retries_cb (sim.c:544)
==2870==    by 0x45544A: service_send_callback (qmi.c:2143)
==2870==    by 0x452D00: handle_packet (qmi.c:815)
==2870==    by 0x452E85: received_data (qmi.c:863)
==2870==    by 0x508DB6C: g_main_context_dispatch (in /lib/x86_64-linux-gnu/libglib-2.0.so.0.4200.1)
==2870==    by 0x508DF47: ??? (in /lib/x86_64-linux-gnu/libglib-2.0.so.0.4200.1)
==2870==    by 0x508E271: g_main_loop_run (in /lib/x86_64-linux-gnu/libglib-2.0.so.0.4200.1)
==2870==    by 0x4C680B: main (main.c:256)
==2870==  Uninitialised value was created by a stack allocation
==2870==    at 0x459B1A: query_pin_retries_cb (sim.c:531)
2021-09-07 20:46:23 +02:00
Denis Kenzior
d0a617d469 qmi: Fix memory leak
==14399== 28 bytes in 4 blocks are definitely lost in loss record 151 of 390
==14399==    at 0x4C2BBAF: malloc (vg_replace_malloc.c:299)
==14399==    by 0x209065: convert_gsm_to_utf8_with_lang (util.c:651)
==14399==    by 0x2091D1: convert_gsm_to_utf8 (util.c:690)
==14399==    by 0x22DDA7: ussd_decode (smsutil.c:4738)
==14399==    by 0x18BF71: qmi_ussd_request (ussd.c:233)
==14399==    by 0x2183EA: ussd_initiate (ussd.c:614)
==14399==    by 0x27B6C8: process_message (object.c:259)
==14399==    by 0x27D1CD: generic_message (object.c:1070)
==14399==    by 0x5170732: ??? (in /lib/x86_64-linux-gnu/libdbus-1.so.3.14.14)
==14399==    by 0x5161D83: dbus_connection_dispatch (in /lib/x86_64-linux-gnu/libdbus-1.so.3.14.14)
==14399==    by 0x27907C: message_dispatch (mainloop.c:72)
==14399==    by 0x4E826A9: g_main_context_dispatch (in /lib/x86_64-linux-gnu/libglib-2.0.so.0.5000.3)
2021-09-07 20:06:26 +02:00
Denis Kenzior
1ba3b32273 qmi: Fix memory leak
==14399== 16 bytes in 8 blocks are definitely lost in loss record 132 of 390
==14399==    at 0x4C2BBAF: malloc (vg_replace_malloc.c:299)
==14399==    by 0x59E03D9: strndup (strndup.c:43)
==14399==    by 0x18277E: qmi_result_get_string (qmi.c:1794)
==14399==    by 0x184221: get_ids_cb (devinfo.c:129)
==14399==    by 0x18353B: service_send_callback (qmi.c:2286)
==14399==    by 0x18093C: handle_packet (qmi.c:831)
==14399==    by 0x180ADD: received_data (qmi.c:880)
==14399==    by 0x4E826A9: g_main_context_dispatch (in /lib/x86_64-linux-gnu/libglib-2.0.so.0.5000.3)
==14399==    by 0x4E82A5F: ??? (in /lib/x86_64-linux-gnu/libglib-2.0.so.0.5000.3)
==14399==    by 0x4E82D81: g_main_loop_run (in /lib/x86_64-linux-gnu/libglib-2.0.so.0.5000.3)
==14399==    by 0x201900: main (main.c:306)
2021-09-07 20:05:00 +02:00
Gabriel Lucas
14b764ac64 gemalto: support ALS3 in gemalto's plugin
Force serial port opening options
Wait for modem to be ready to start
initializing it
Handle LTE
2021-09-07 20:03:52 +02:00
Bassem Boubaker
b808bfad17 gemalto: Add more details in setup_gemalto comment
ALS3, PLS8-E and PLS8-X have same vid/pid with same enumeration process
2021-09-07 19:53:46 +02:00
Denis Kenzior
82d62a8f50 AUTHORS: Mention Bassem's contributions 2021-09-07 19:52:07 +02:00
Bassem Boubaker
23d6263e3c cdma-netreg: Fix emission of PropertyChanged 2021-09-07 19:51:01 +02:00
Denis Kenzior
ac3192204c AUTHORS: Mention Mariem's contributions 2021-09-07 19:49:54 +02:00
Mariem Cherif
5ad2617ecd gemalto: acquire the network technology 2021-09-07 19:48:21 +02:00
Gabriel Lucas
890842b3af gemalto: add detection of ALS3 modem
The product ID is added to the list of
modems to be detected by Ofono.
The gemalto plugin is used to handle the
ALS3 modem.
2021-09-07 19:47:25 +02:00
Denis Kenzior
06de44299a plugins: Update to the new LTE API 2021-09-07 19:39:51 +02:00
Denis Kenzior
77b2eec613 ubloxmodem: Update to the new LTE API 2021-09-07 19:37:07 +02:00
Denis Kenzior
12ccd7cd46 rilmodem: Update to the new LTE API 2021-09-07 19:35:59 +02:00
Denis Kenzior
8f09880d52 qmimodem: Update to the new LTE API 2021-09-07 19:31:48 +02:00
Denis Kenzior
ee5f91221b atmodem: Update to the new lte API 2021-09-07 19:29:08 +02:00
Denis Kenzior
c03c6f4215 lte: update to the new API 2021-09-07 19:25:27 +02:00
Denis Kenzior
c49e2d8723 include: Add missing vendor parameter to lte atom 2021-09-07 19:13:37 +02:00
Slava Monich
deecd829a6 Merge pull request #5 from sailfishos/jb55388
Remove incorrect hardcoded tech value.
2021-09-07 16:49:39 +03:00
Matti Lehtimäki
3acf91c6a9 [ril] Remove incorrect hardcoded tech value. JB#55388 2021-09-06 20:44:26 +03:00
Marcel Holtmann
85b61c8964 call-forwarding: Increase string buffer to avoid overflow 2021-08-26 03:03:55 +03:00
Jonas Bonn
8986749585 atmodem: enlarge command buffer
The ofono phone number max length is 80 so a buffer size of 64 is
obviously insufficient.  Expanding the buffer to 128 prevents a
potential failure and suppresses the folowing compiler warning:

../drivers/atmodem/sms.c: In function ‘at_csca_set’:
../drivers/atmodem/sms.c:108:40: warning: ‘%s’ directive output may be truncated writing up to 80 bytes into a region of size 55 [-Wformat-truncation=]
  snprintf(buf, sizeof(buf), "AT+CSCA=\"%s\",%d", sca->number, sca->type);
                                        ^~
../drivers/atmodem/sms.c:108:2: note: ‘snprintf’ output between 13 and 103 bytes into a destination of size 64
  snprintf(buf, sizeof(buf), "AT+CSCA=\"%s\",%d", sca->number, sca->type);
  ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
2021-08-26 03:03:55 +03:00
Juho Hämäläinen
1c0f5094a6 Merge pull request #3 from jusa/jb55276
Be less pedantic about ordering of speech codecs.
2021-08-25 17:00:06 +03:00
Juho Hämäläinen
4208b6d9ea [bluetooth] Be less pedantic about ordering of speech codecs. Fixes JB#55276
HFP spec 1.7.1 (4.34.1) says:

The Codec ID for the mandatory narrow band codec (CVSD) shall
always be included.

If wide band speech is supported, then the mandatory codec (mSBC)
shall be included unless it is temporarily unavailable.

Any other optional wide band speech codecs may also be included
in this list as long as the mandatory codec is included first.

---

The wording in spec is slightly vague on what the ordering of
mandatory narrow band codec (CVSD) and - IF wide band speech
is supported - mandatory wide band coded (mSBC) should be.
oFono's take is that the mandatory narrow band codec should
be listed first, and when mSBC is there oFono will abort the
connection.

To fix this we can be less pedantic about the ordering of
codecs - as long as the mandatory ones are there.
2021-08-25 16:32:55 +03:00
Frajo
59e304d474 Merge pull request #2 from krnlyng/jb55233
[packaging] Use transfiletriggerin to restart ofono when a plugin is installed. JB#55233
2021-08-25 16:02:24 +03:00
Frajo Haider
30a2424507 [packaging] Use transfiletriggerin to restart ofono when a plugin is installed. JB#55233 2021-08-24 13:29:18 +03:00
Slava Monich
e4f3ec6322 Merge pull request #1 from monich/start_block
Fix SIM I/O mess
2021-07-30 15:12:59 +03:00
Slava Monich
95fd4efc37 [simfs] Fix SIM I/O mess. JB#54380
Apparently all simfs reads from any blocks other than the very first one
were badly broken and could even cause a crash :|
2021-07-30 01:50:07 +03:00
Slava Monich
ef5ee98508 [ofono] Set destination for Unsubscribed signal. JB#50816 2021-06-10 18:00:39 +03:00
Slava Monich
4220e7d5e8 Merge branch 'dbus-clients-fixes' into 'master'
Resolve a few issues with cell info notifications

See merge request mer-core/ofono!286
2021-06-10 13:54:42 +00:00
Slava Monich
33c067a75f [ofono] Resolved a few issues with cell info notifications. JB#50816
1. Disable notifications from modem on unsibscribe
2. Made all signals unicast
3. Fixed a memory leak
2021-06-10 16:23:52 +03:00
Slava Monich
29616c04d0 [ofono] Fixed signal emission, reworked D-Bus client list. JB#50816
1. Exposed D-Bus clients list to plugin as ofono_dbus_clients
2. Signal has to be properly declared, otherwise it's not emitted
3. Added missing unit tests
2021-06-10 05:10:16 +03:00
Slava Monich
beb997d914 Merge branch 'jb50608-ondemand' into 'master'
Disable cell info updates when no one listens for them

See merge request mer-core/ofono!274
2021-06-10 01:58:05 +00:00
Slava Monich
cefc03e5ed Merge branch 'pcscf' into 'master'
Expose P-CSCF address(es) over D-Bus

See merge request mer-core/ofono!285
2021-06-03 21:29:06 +00:00
Slava Monich
85d99536ee Merge branch 'mtu' into 'master'
Don't limit MTU for non-MMS contexts

See merge request mer-core/ofono!284
2021-06-03 21:28:08 +00:00
Slava Monich
ea36baa4c1 [ril] Don't limit MTU for non-MMS contexts
Larger MTU means better throughput, and the original problem for which
this workaround was implemented was specific to MMS. There's no reason
to limit MTU for other data connections.
2021-06-03 19:49:38 +03:00
Slava Monich
b95a089c00 [ril] Provide P-CSCF address to the core. JB#48905
Also optimized reporting of DNS addresses by not setting empty lists.
If nothing else, that slightly reduces the amount of D-Bus traffic.
2021-06-03 19:36:52 +03:00
Slava Monich
c8dbf5494b [ofono] Expose P-CSCF address(es) via D-Bus. JB#48905 2021-06-03 19:01:01 +03:00
Slava Monich
cfb75f473d [sim] Fixed AID comparison. JB#54048
It worked only because aid was the first field in the struct.
2021-06-03 04:24:46 +03:00
Denis Grigorev
3d147843c4 [ril] Make cell info updates unicast. JB#50608 2021-05-28 16:25:42 +03:00
Denis Grigorev
c01dc63cbc [ril] Cell info consumer can unsubscribe from updates. JB#50608
Add a new org.nemomobile.ofono.CellInfo.Unsubscribe method. If it is called
ofono excludes the client from cell info consumers. The updates will be
disabled if no one client left.
2021-05-28 16:25:42 +03:00
Denis Grigorev
297926ed24 [ril] Enable cell info updates only when requested. JB#50608 2021-05-28 16:25:42 +03:00
Denis Grigorev
6ef1174ea8 [ril] Cell info updates can be disabled. JB#50608 2021-05-28 16:25:42 +03:00
155 changed files with 10697 additions and 8495 deletions

15
ofono/.gitignore vendored
View File

@@ -9,7 +9,7 @@ Makefile.in
aclocal.m4
config.guess
config.h
config.h.in
config.h.in*
config.log
config.status
config.sub
@@ -42,9 +42,13 @@ unit/test-sms-root
unit/test-simutil
unit/test-mux
unit/test-caif
unit/test-cell-info
unit/test-cell-info-dbus
unit/test-stkutil
unit/test-cdmasms
unit/test-conf
unit/test-dbus-access
unit/test-dbus-clients
unit/test-dbus-queue
unit/test-gprs-filter
unit/test-ril_config
@@ -57,13 +61,10 @@ unit/test-rilmodem-cs
unit/test-rilmodem-gprs
unit/test-rilmodem-sms
unit/test-sailfish_access
unit/test-sailfish_cell_info
unit/test-sailfish_cell_info_dbus
unit/test-sailfish_manager
unit/test-sailfish_sim_info
unit/test-sailfish_sim_info_dbus
unit/test-config
unit/test-slot-manager
unit/test-watch
unit/test-sim-info
unit/test-sim-info-dbus
unit/test-sms-filter
unit/test-voicecall-filter
unit/test-*.log

View File

@@ -130,3 +130,8 @@ Joey Hewitt <joey@joeyhewitt.com>
Richard Röjfors <richard.rojfors@gmail.com>
Philippe De Swert <philippe.deswert@nomovok.com>
Gabriel Lucas <gabriel.lucas@smile.fr>
Mariem Cherif <mariem.cherif@ardia.com.tn>
Bassem Boubaker <bassem.boubaker@actia.fr>
Bob Ham <bob.ham@puri.sm>
Varun Gargi <varun.gargi@intel.com>
Florent Beillonnet <florent.beillonnet@gmail.com>

View File

@@ -1,3 +1,16 @@
ver 1.24:
Fix issue with property changed signals and CDMA networks.
Fix issue with handling SIM filesystem and SIM removal.
Fix issue with handling PIN state and incorrect codes.
Fix issue with handling of parsing AID type.
Fix issue with SIM detection and QMI devices.
Fix issue with PIN handling and QMI devices.
Fix issue with USSD handling and QMI devices.
Fix issue with handling USSD TERMINATED response.
Fix issue with handling USSD reset and STK REFRESH.
Add support for detecting Gemalto ALS3 modems.
Add support for SIMCom based SIM7100E modems.
ver 1.23:
Fix issue with handling SIM AID sessions.
Add support for QMI LTE bearer handling.

View File

@@ -26,9 +26,11 @@ pkginclude_HEADERS = include/log.h include/plugin.h include/history.h \
include/sms-filter.h include/gprs-filter.h \
include/voicecall-filter.h include/dbus-access.h \
include/ril-constants.h include/ril-transport.h \
include/watch.h gdbus/gdbus.h \
include/watch.h gdbus/gdbus.h include/dbus-clients.h \
include/netmon.h include/lte.h include/ims.h \
include/storage.h
include/slot.h include/cell-info.h \
include/storage.h include/conf.h include/misc.h \
include/mtu-limit.h
nodist_pkginclude_HEADERS = include/version.h
@@ -119,22 +121,15 @@ builtin_modules += udevng
builtin_sources += plugins/udevng.c
endif
if SAILFISH_MANAGER
builtin_modules += sailfish_manager
builtin_sources += plugins/sailfish_manager/sailfish_cell_info.c \
plugins/sailfish_manager/sailfish_cell_info_dbus.c \
plugins/sailfish_manager/sailfish_manager.c \
plugins/sailfish_manager/sailfish_manager_dbus.c \
plugins/sailfish_manager/sailfish_sim_info.c \
plugins/sailfish_manager/sailfish_sim_info_dbus.c
endif
if SAILFISH_ACCESS
builtin_modules += sailfish_access
builtin_sources += plugins/sailfish_access.c
endif
if DATAFILES
dist_conf_DATA += drivers/ril/ril_subscription.conf
endif
if RILMODEM
if SAILFISH_RILMODEM
@@ -181,10 +176,6 @@ builtin_sources += drivers/ril/ril_call_barring.c \
# Vendor specific extensions
builtin_sources += drivers/ril/ril_vendor_mtk.c
if DATAFILES
dist_conf_DATA += drivers/ril/ril_subscription.conf
endif
else
builtin_sources += $(gril_sources)
@@ -573,6 +564,12 @@ builtin_sources += plugins/samsung.c
builtin_modules += sim900
builtin_sources += plugins/sim900.c
builtin_modules += sim7100
builtin_sources += plugins/sim7100.c
builtin_modules += connman
builtin_sources += plugins/connman.c
builtin_modules += telit
builtin_sources += plugins/telit.c
@@ -748,7 +745,6 @@ endif
sbin_PROGRAMS = src/ofonod
src_ofonod_SOURCES = $(builtin_sources) $(gatchat_sources) src/ofono.ver \
src/mtu-watch.c \
src/main.c src/ofono.h src/log.c src/plugin.c \
src/modem.c src/common.h src/common.c \
src/manager.c src/dbus.c src/util.h src/util.c \
@@ -775,11 +771,15 @@ src_ofonod_SOURCES = $(builtin_sources) $(gatchat_sources) src/ofono.ver \
src/handsfree-audio.c src/bluetooth.h \
src/sim-mnclength.c src/voicecallagent.c \
src/sms-filter.c src/gprs-filter.c \
src/dbus-queue.c src/dbus-access.c src/config.c \
src/dbus-clients.c src/dbus-queue.c src/dbus-access.c \
src/voicecall-filter.c src/ril-transport.c \
src/hfp.h src/siri.c src/watchlist.c \
src/netmon.c src/lte.c src/ims.c \
src/netmonagent.c src/netmonagent.h
src/netmonagent.c src/netmonagent.h \
src/slot-manager.c src/slot-manager-dbus.c \
src/cell-info.c src/cell-info-dbus.c \
src/sim-info.c src/sim-info-dbus.c \
src/conf.c src/mtu-limit.c
src_ofonod_LDADD = gdbus/libgdbus-internal.la $(builtin_libadd) \
@GLIB_LIBS@ @DBUS_LIBS@ -ldl
@@ -806,8 +806,7 @@ AM_CFLAGS = @DBUS_CFLAGS@ @GLIB_CFLAGS@ $(builtin_cflags) \
AM_CPPFLAGS = -I$(builddir)/include -I$(builddir)/src -I$(srcdir)/src \
-I$(srcdir)/gdbus -I$(srcdir)/gisi -I$(srcdir)/gatchat \
-I$(srcdir)/btio -I$(srcdir)/gril \
-I$(srcdir)/plugins/sailfish_manager
-I$(srcdir)/btio -I$(srcdir)/gril
doc_files = doc/overview.txt doc/ofono-paper.txt doc/release-faq.txt \
doc/manager-api.txt doc/modem-api.txt doc/network-api.txt \
@@ -967,61 +966,50 @@ unit_tests = unit/test-common unit/test-util unit/test-idmap \
unit/test-simutil unit/test-stkutil \
unit/test-sms unit/test-cdmasms
if SAILFISH_MANAGER
unit_test_cell_info_SOURCES = unit/test-cell-info.c src/cell-info.c src/log.c
unit_test_cell_info_CFLAGS = $(AM_CFLAGS) $(COVERAGE_OPT)
unit_test_cell_info_LDADD = @GLIB_LIBS@ -ldl
unit_objects += $(unit_test_cell_info_OBJECTS)
unit_tests += unit/test-cell-info
unit_test_sailfish_cell_info_SOURCES = unit/test-sailfish_cell_info.c \
plugins/sailfish_manager/sailfish_cell_info.c
unit_test_sailfish_cell_info_CFLAGS = $(AM_CFLAGS) $(COVERAGE_OPT)
unit_test_sailfish_cell_info_LDADD = @GLIB_LIBS@ -ldl
unit_objects += $(unit_test_sailfish_cell_info_OBJECTS)
unit_tests += unit/test-sailfish_cell_info
unit_test_sailfish_cell_info_dbus_SOURCES = unit/test-dbus.c \
unit/test-sailfish_cell_info_dbus.c \
unit/fake_sailfish_cell_info.c \
plugins/sailfish_manager/sailfish_cell_info.c \
plugins/sailfish_manager/sailfish_cell_info_dbus.c \
gdbus/object.c \
unit_test_cell_info_dbus_SOURCES = unit/test-dbus.c \
unit/test-cell-info-dbus.c unit/fake_cell_info.c \
src/cell-info.c src/cell-info-dbus.c \
gdbus/object.c src/dbus-clients.c \
src/dbus.c src/log.c
unit_test_sailfish_cell_info_dbus_CFLAGS = $(AM_CFLAGS) $(COVERAGE_OPT) \
unit_test_cell_info_dbus_CFLAGS = $(AM_CFLAGS) $(COVERAGE_OPT) \
@DBUS_GLIB_CFLAGS@
unit_test_sailfish_cell_info_dbus_LDADD = @DBUS_GLIB_LIBS@ @GLIB_LIBS@ -ldl
unit_objects += $(unit_test_sailfish_cell_info_dbus_OBJECTS)
unit_tests += unit/test-sailfish_cell_info_dbus
unit_test_cell_info_dbus_LDADD = @DBUS_GLIB_LIBS@ @GLIB_LIBS@ -ldl
unit_objects += $(unit_test_cell_info_dbus_OBJECTS)
unit_tests += unit/test-cell-info-dbus
unit_test_sailfish_sim_info_SOURCES = unit/test-sailfish_sim_info.c \
unit/fake_watch.c \
plugins/sailfish_manager/sailfish_sim_info.c \
src/storage.c src/watchlist.c src/log.c
unit_test_sailfish_sim_info_CFLAGS = $(COVERAGE_OPT) $(AM_CFLAGS) \
unit_test_sim_info_SOURCES = unit/test-sim-info.c unit/fake_watch.c \
src/sim-info.c src/storage.c src/watchlist.c src/log.c
unit_test_sim_info_CFLAGS = $(COVERAGE_OPT) $(AM_CFLAGS) \
-DSTORAGEDIR='"/tmp/ofono"'
unit_test_sailfish_sim_info_LDADD = @GLIB_LIBS@ -ldl
unit_objects += $(unit_test_sailfish_sim_info_OBJECTS)
unit_tests += unit/test-sailfish_sim_info
unit_test_sim_info_LDADD = @GLIB_LIBS@ -ldl
unit_objects += $(unit_test_sim_info_OBJECTS)
unit_tests += unit/test-sim-info
unit_test_sailfish_sim_info_dbus_SOURCES = unit/test-sailfish_sim_info_dbus.c \
unit_test_sim_info_dbus_SOURCES = unit/test-sim-info-dbus.c \
unit/test-dbus.c unit/fake_watch.c \
plugins/sailfish_manager/sailfish_sim_info.c \
plugins/sailfish_manager/sailfish_sim_info_dbus.c \
src/sim-info.c src/sim-info-dbus.c \
gdbus/object.c \
src/dbus.c src/storage.c src/watchlist.c src/log.c
unit_test_sailfish_sim_info_dbus_CFLAGS = $(COVERAGE_OPT) $(AM_CFLAGS) \
unit_test_sim_info_dbus_CFLAGS = $(COVERAGE_OPT) $(AM_CFLAGS) \
@DBUS_GLIB_CFLAGS@ -DSTORAGEDIR='"/tmp/ofono"'
unit_test_sailfish_sim_info_dbus_LDADD = @DBUS_GLIB_LIBS@ @GLIB_LIBS@ -ldl
unit_objects += $(unit_test_sailfish_sim_info_dbus_OBJECTS)
unit_tests += unit/test-sailfish_sim_info_dbus
unit_test_sim_info_dbus_LDADD = @DBUS_GLIB_LIBS@ @GLIB_LIBS@ -ldl
unit_objects += $(unit_test_sim_info_dbus_OBJECTS)
unit_tests += unit/test-sim-info-dbus
unit_test_sailfish_manager_SOURCES = unit/test-sailfish_manager.c \
unit/fake_watch.c \
plugins/sailfish_manager/sailfish_manager.c \
plugins/sailfish_manager/sailfish_cell_info.c \
plugins/sailfish_manager/sailfish_sim_info.c \
unit_test_slot_manager_SOURCES = unit/test-slot-manager.c unit/fake_watch.c \
src/slot-manager.c src/cell-info.c src/sim-info.c \
src/storage.c src/log.c
unit_test_sailfish_manager_CFLAGS = $(AM_CFLAGS) $(COVERAGE_OPT) \
unit_test_slot_manager_CFLAGS = $(AM_CFLAGS) $(COVERAGE_OPT) \
-DSTORAGEDIR='"/tmp/ofono"'
unit_test_sailfish_manager_LDADD = @GLIB_LIBS@ -ldl
unit_objects += $(unit_test_sailfish_manager_OBJECTS)
unit_tests += unit/test-sailfish_manager
unit_test_slot_manager_LDADD = @GLIB_LIBS@ -ldl
unit_objects += $(unit_test_slot_manager_OBJECTS)
unit_tests += unit/test-slot-manager
unit_test_watch_SOURCES = unit/test-watch.c src/watch.c \
src/log.c src/watchlist.c
@@ -1031,15 +1019,6 @@ unit_test_watch_LDADD = @GLIB_LIBS@ -ldl
unit_objects += $(unit_test_watch_OBJECTS)
unit_tests += unit/test-watch
endif
unit_test_config_SOURCES = unit/test-config.c drivers/ril/ril_util.c \
src/config.c src/log.c
unit_test_config_CFLAGS = $(COVERAGE_OPT) $(AM_CFLAGS)
unit_test_config_LDADD = @GLIB_LIBS@ -ldl
unit_objects += $(unit_test_config_OBJECTS)
unit_tests += unit/test-config
if SAILFISH_ACCESS
unit_test_sailfish_access_SOURCES = unit/test-sailfish_access.c \
plugins/sailfish_access.c src/dbus-access.c src/log.c
@@ -1059,8 +1038,15 @@ unit_tests += unit/test-dbus-access
if RILMODEM
if SAILFISH_RILMODEM
unit_test_conf_SOURCES = unit/test-conf.c drivers/ril/ril_util.c \
src/conf.c src/util.c src/log.c
unit_test_conf_CFLAGS = $(COVERAGE_OPT) $(AM_CFLAGS)
unit_test_conf_LDADD = @GLIB_LIBS@ -ldl
unit_objects += $(unit_test_conf_OBJECTS)
unit_tests += unit/test-conf
unit_test_ril_config_SOURCES = unit/test-ril_config.c drivers/ril/ril_util.c \
drivers/ril/ril_config.c src/log.c
drivers/ril/ril_config.c src/conf.c src/util.c src/log.c
unit_test_ril_config_CFLAGS = $(COVERAGE_OPT) $(AM_CFLAGS)
unit_test_ril_config_LDADD = @GLIB_LIBS@ -ldl
unit_objects += $(unit_test_ril_config_OBJECTS)
@@ -1074,7 +1060,7 @@ unit_objects += $(unit_test_ril_ecclist_OBJECTS)
unit_tests += unit/test-ril_ecclist
unit_test_ril_util_SOURCES = unit/test-ril_util.c drivers/ril/ril_util.c \
src/log.c
src/util.c src/log.c
unit_test_ril_util_CFLAGS = $(COVERAGE_OPT) $(AM_CFLAGS)
unit_test_ril_util_LDADD = @GLIB_LIBS@ -ldl
unit_objects += $(unit_test_ril_util_OBJECTS)
@@ -1082,7 +1068,7 @@ unit_tests += unit/test-ril_util
unit_test_ril_vendor_SOURCES = unit/test-ril_vendor.c unit/fake_watch.c \
drivers/ril/ril_vendor.c drivers/ril/ril_vendor_mtk.c \
drivers/ril/ril_util.c src/log.c
drivers/ril/ril_util.c src/util.c src/log.c
unit_test_ril_vendor_CFLAGS = $(COVERAGE_OPT) $(AM_CFLAGS)
unit_test_ril_vendor_LDADD = @GLIB_LIBS@ -ldl
unit_objects += $(unit_test_ril_vendor_OBJECTS)
@@ -1164,6 +1150,14 @@ unit_test_caif_CFLAGS = $(COVERAGE_OPT) $(AM_CFLAGS)
unit_test_caif_LDADD = @GLIB_LIBS@
unit_objects += $(unit_test_caif_OBJECTS)
unit_test_dbus_clients_SOURCES = unit/test-dbus-clients.c unit/test-dbus.c \
src/dbus-clients.c gdbus/object.c \
src/dbus.c src/log.c
unit_test_dbus_clients_CFLAGS = @DBUS_GLIB_CFLAGS@ $(COVERAGE_OPT) $(AM_CFLAGS)
unit_test_dbus_clients_LDADD = @DBUS_GLIB_LIBS@ @GLIB_LIBS@ -ldl
unit_objects += $(unit_test_dbus_clients_OBJECTS)
unit_tests += unit/test-dbus-clients
unit_test_dbus_queue_SOURCES = unit/test-dbus-queue.c unit/test-dbus.c \
src/dbus-queue.c gdbus/object.c \
src/dbus.c src/log.c

View File

@@ -1,5 +1,5 @@
AC_PREREQ(2.60)
AC_INIT(ofono, 1.23)
AC_INIT(ofono, 1.24)
AM_INIT_AUTOMAKE([foreign subdir-objects color-tests])
AC_CONFIG_HEADERS(config.h)
@@ -183,8 +183,8 @@ AC_ARG_ENABLE(sailfish-rilmodem, AC_HELP_STRING([--enable-sailfish-rilmodem],
[enable_sailfish_rilmodem="no"])
AM_CONDITIONAL(SAILFISH_RILMODEM, test "${enable_sailfish_rilmodem}" != "no")
PKG_CHECK_MODULES(GLIBUTIL, libglibutil >= 1.0.35, dummy=yes,
AC_MSG_ERROR(libglibutil >= 1.0.35 is required))
PKG_CHECK_MODULES(GLIBUTIL, libglibutil >= 1.0.49, dummy=yes,
AC_MSG_ERROR(libglibutil >= 1.0.49 is required))
CFLAGS="$CFLAGS $GLIBUTIL_CFLAGS"
LIBS="$LIBS $GLIBUTIL_LIBS"

View File

@@ -278,6 +278,13 @@ Properties boolean Active [readwrite]
via this proxy. All other values are left
out in this case.
array{string} ProxyCSCF [readonly, optional]
Holds the list of P-CSCF (SIP proxy) for this
context. Only used by IMS connections.
This is a Sailfish OS specific extension.
dict IPv6.Settings [readonly, optional]
Holds all the IPv6 network settings
@@ -304,6 +311,13 @@ Properties boolean Active [readwrite]
Holds the gateway IP for this connection.
array{string} ProxyCSCF [readonly, optional]
Holds the list of P-CSCF (SIP proxy) for this
context. Only used by IMS connections.
This is a Sailfish OS specific extension.
string MessageProxy [readwrite, MMS only]
Holds the MMS Proxy setting.

View File

@@ -48,6 +48,51 @@ struct cbs_data {
unsigned int vendor;
};
static void at_xmm_etw_sec_notify(GAtResult *result, gpointer user_data)
{
struct ofono_cbs *cbs = user_data;
const char *hexpdu;
int pdulen;
GAtResultIter iter;
unsigned char pdu[88];
long hexpdulen;
DBG("");
g_at_result_iter_init(&iter, result);
if (!g_at_result_iter_next(&iter, "+XETWSECWARN:"))
return;
if (!g_at_result_iter_next_number(&iter, &pdulen))
return;
if (pdulen != 88) {
ofono_error("Got a CBM message with invalid PDU size!");
return;
}
hexpdu = g_at_result_pdu(result);
if (hexpdu == NULL) {
ofono_error("Got a CBM, but no PDU. Are we in text mode?");
return;
}
DBG("Got new Cell Broadcast via XETWSECWARN: %s, %d", hexpdu, pdulen);
if (decode_hex_own_buf(hexpdu, -1, &hexpdulen, 0, pdu) == NULL) {
ofono_error("Unable to hex-decode the PDU");
return;
}
if (hexpdulen != pdulen) {
ofono_error("hexpdu length not equal to reported pdu length");
return;
}
ofono_cbs_notify(cbs, pdu, pdulen);
}
static void at_cbm_notify(GAtResult *result, gpointer user_data)
{
struct ofono_cbs *cbs = user_data;
@@ -124,6 +169,10 @@ static void at_cbs_set_topics(struct ofono_cbs *cbs, const char *topics,
g_at_chat_send(data->chat, "AT+CSCB=0", none_prefix,
NULL, NULL, NULL);
break;
case OFONO_VENDOR_XMM:
g_at_chat_send(data->chat, "AT+XETWNTFYSTART=2", none_prefix,
NULL, NULL, NULL);
break;
default:
break;
}
@@ -151,6 +200,10 @@ static void at_cbs_clear_topics(struct ofono_cbs *cbs,
DBG("");
if (data->vendor == OFONO_VENDOR_XMM)
g_at_chat_send(data->chat, "AT+XETWNTFYSTOP=2", none_prefix,
NULL, NULL, NULL);
if (g_at_chat_send(data->chat, "AT+CSCB=0", none_prefix,
at_cscb_set_cb, cbd, g_free) > 0)
return;
@@ -175,6 +228,10 @@ static void at_cbs_register(gboolean ok, GAtResult *result, gpointer user)
*/
g_at_chat_register(data->chat, "+CBM:", at_cbm_notify, TRUE, cbs, NULL);
if (data->vendor == OFONO_VENDOR_XMM)
g_at_chat_register(data->chat, "+XETWSECWARN:",
at_xmm_etw_sec_notify, TRUE, cbs, NULL);
ofono_cbs_register(cbs);
}
@@ -223,6 +280,13 @@ static int at_cbs_probe(struct ofono_cbs *cbs, unsigned int vendor,
ofono_cbs_set_data(cbs, data);
if (vendor == OFONO_VENDOR_XMM) {
g_at_chat_send(data->chat, "AT+XCMAS=1", cscb_prefix,
NULL, NULL, NULL);
g_at_chat_send(data->chat, "AT+XETWCFG=1,1,0,0; ", none_prefix,
NULL, NULL, NULL);
}
g_at_chat_send(data->chat, "AT+CSCB=?", cscb_prefix,
at_cscb_support_cb, cbs, NULL);

View File

@@ -91,7 +91,7 @@ static gboolean lte_delayed_register(gpointer user_data)
return FALSE;
}
static int at_lte_probe(struct ofono_lte *lte, void *data)
static int at_lte_probe(struct ofono_lte *lte, unsigned int vendor, void *data)
{
GAtChat *chat = data;
struct lte_driver_data *ldd;

View File

@@ -48,6 +48,7 @@ static const char *cops_prefix[] = { "+COPS:", NULL };
static const char *csq_prefix[] = { "+CSQ:", NULL };
static const char *cind_prefix[] = { "+CIND:", NULL };
static const char *cmer_prefix[] = { "+CMER:", NULL };
static const char *smoni_prefix[] = { "^SMONI:", NULL };
static const char *zpas_prefix[] = { "+ZPAS:", NULL };
static const char *option_tech_prefix[] = { "_OCTI:", "_OUWCTI:", NULL };
@@ -178,6 +179,31 @@ static int option_parse_tech(GAtResult *result)
return tech;
}
static int cinterion_parse_tech(GAtResult *result)
{
int tech = -1;
GAtResultIter iter;
const char *technology;
g_at_result_iter_init(&iter, result);
if (!g_at_result_iter_next(&iter, "^SMONI: "))
return tech;
if (!g_at_result_iter_next_unquoted_string(&iter, &technology))
return tech;
if (strcmp(technology, "2G") == 0) {
tech = ACCESS_TECHNOLOGY_GSM_EGPRS;
} else if (strcmp(technology, "3G") == 0) {
tech = ACCESS_TECHNOLOGY_UTRAN;
} else if (strcmp(technology, "4G") == 0) {
tech = ACCESS_TECHNOLOGY_EUTRAN;
}
return tech;
}
static void at_creg_cb(gboolean ok, GAtResult *result, gpointer user_data)
{
struct cb_data *cbd = user_data;
@@ -205,6 +231,18 @@ static void at_creg_cb(gboolean ok, GAtResult *result, gpointer user_data)
cb(&error, status, lac, ci, tech, cbd->data);
}
static void cinterion_query_tech_cb(gboolean ok, GAtResult *result,
gpointer user_data)
{
struct tech_query *tq = user_data;
int tech;
tech = cinterion_parse_tech(result);
ofono_netreg_status_notify(tq->netreg,
tq->status, tq->lac, tq->ci, tech);
}
static void zte_tech_cb(gboolean ok, GAtResult *result, gpointer user_data)
{
struct cb_data *cbd = user_data;
@@ -1518,6 +1556,12 @@ static void creg_notify(GAtResult *result, gpointer user_data)
option_query_tech_cb, tq, g_free) > 0)
return;
break;
case OFONO_VENDOR_CINTERION:
if (g_at_chat_send(nd->chat, "AT^SMONI",
smoni_prefix,
cinterion_query_tech_cb, tq, g_free) > 0)
return;
break;
}
g_free(tq);

View File

@@ -1359,12 +1359,12 @@ static void at_pin_send_puk(struct ofono_sim *sim, const char *puk,
char buf[64];
int ret;
cbd->user = sd;
cbd->user = sim;
snprintf(buf, sizeof(buf), "AT+CPIN=\"%s\",\"%s\"", puk, passwd);
ret = g_at_chat_send(sd->chat, buf, none_prefix,
at_pin_send_cb, cbd, NULL);
at_pin_send_cb, cbd, g_free);
memset(buf, 0, sizeof(buf));

View File

@@ -104,7 +104,7 @@ static void at_csca_set(struct ofono_sms *sms,
{
struct sms_data *data = ofono_sms_get_data(sms);
struct cb_data *cbd = cb_data_new(cb, user_data);
char buf[64];
char buf[128];
snprintf(buf, sizeof(buf), "AT+CSCA=\"%s\",%d", sca->number, sca->type);

View File

@@ -1120,6 +1120,7 @@ static int at_voicecall_probe(struct ofono_voicecall *vc, unsigned int vendor,
switch (vd->vendor) {
case OFONO_VENDOR_QUALCOMM_MSM:
case OFONO_VENDOR_SIMCOM:
g_at_chat_send(vd->chat, "AT+COLP=0", NULL, NULL, NULL, NULL);
break;
default:

View File

@@ -129,6 +129,7 @@ static void get_ids_cb(struct qmi_result *result, void *user_data)
str = qmi_result_get_string(result, QMI_DMS_RESULT_ESN);
/* Telit qmi modems return a "0" string when ESN is not available. */
if (!str || strcmp(str, "0") == 0) {
qmi_free(str);
str = qmi_result_get_string(result, QMI_DMS_RESULT_IMEI);
if (!str) {
CALLBACK_WITH_FAILURE(cb, NULL, cbd->data);

View File

@@ -212,7 +212,8 @@ error:
ofono_lte_register(lte);
}
static int qmimodem_lte_probe(struct ofono_lte *lte, void *data)
static int qmimodem_lte_probe(struct ofono_lte *lte,
unsigned int vendor, void *data)
{
struct qmi_device *device = data;
struct lte_data *ldd;

View File

@@ -47,6 +47,13 @@ struct discovery {
qmi_destroy_func_t destroy;
};
struct qmi_version {
uint8_t type;
uint16_t major;
uint16_t minor;
const char *name;
};
struct qmi_device {
int ref_count;
int fd;
@@ -80,7 +87,6 @@ struct qmi_device {
struct qmi_service {
int ref_count;
struct qmi_device *device;
bool shared;
uint8_t type;
uint16_t major;
uint16_t minor;
@@ -161,25 +167,25 @@ void qmi_free(void *ptr)
static struct qmi_request *__request_alloc(uint8_t service,
uint8_t client, uint16_t message,
uint16_t headroom, const void *data,
const void *data,
uint16_t length, qmi_message_func_t func,
void *user_data, void **head)
void *user_data)
{
struct qmi_request *req;
struct qmi_mux_hdr *hdr;
struct qmi_message_hdr *msg;
uint16_t headroom;
req = g_try_new0(struct qmi_request, 1);
if (!req)
return NULL;
req = g_new0(struct qmi_request, 1);
if (service == QMI_SERVICE_CONTROL)
headroom = QMI_CONTROL_HDR_SIZE;
else
headroom = QMI_SERVICE_HDR_SIZE;
req->len = QMI_MUX_HDR_SIZE + headroom + QMI_MESSAGE_HDR_SIZE + length;
req->buf = g_try_malloc(req->len);
if (!req->buf) {
g_free(req);
return NULL;
}
req->buf = g_malloc(req->len);
req->client = client;
@@ -203,8 +209,6 @@ static struct qmi_request *__request_alloc(uint8_t service,
req->callback = func;
req->user_data = user_data;
*head = req->buf + QMI_MUX_HDR_SIZE;
return req;
}
@@ -256,9 +260,6 @@ static gboolean __service_compare_shared(gpointer key, gpointer value,
struct qmi_service *service = value;
uint8_t type = GPOINTER_TO_UINT(user_data);
if (!service->shared)
return FALSE;
if (service->type == type)
return TRUE;
@@ -695,14 +696,37 @@ static void wakeup_writer(struct qmi_device *device)
can_write_data, device, write_watch_destroy);
}
static void __request_submit(struct qmi_device *device,
struct qmi_request *req, uint16_t transaction)
static uint16_t __request_submit(struct qmi_device *device,
struct qmi_request *req)
{
req->tid = transaction;
struct qmi_mux_hdr *mux;
mux = req->buf;
if (mux->service == QMI_SERVICE_CONTROL) {
struct qmi_control_hdr *hdr;
hdr = req->buf + QMI_MUX_HDR_SIZE;
hdr->type = 0x00;
hdr->transaction = device->next_control_tid++;
if (device->next_control_tid == 0)
device->next_control_tid = 1;
req->tid = hdr->transaction;
} else {
struct qmi_service_hdr *hdr;
hdr = req->buf + QMI_MUX_HDR_SIZE;
hdr->type = 0x00;
hdr->transaction = device->next_service_tid++;
if (device->next_service_tid < 256)
device->next_service_tid = 256;
req->tid = hdr->transaction;
}
g_queue_push_tail(device->req_queue, req);
wakeup_writer(device);
return req->tid;
}
static void service_notify(gpointer key, gpointer value, gpointer user_data)
@@ -961,6 +985,9 @@ struct qmi_device *qmi_device_new(int fd)
device->service_list = g_hash_table_new_full(g_direct_hash,
g_direct_equal, NULL, service_destroy);
device->next_control_tid = 1;
device->next_service_tid = 256;
return device;
}
@@ -1078,6 +1105,41 @@ static const void *tlv_get(const void *data, uint16_t size,
return NULL;
}
bool qmi_device_get_service_version(struct qmi_device *device, uint8_t type,
uint16_t *major, uint16_t *minor)
{
struct qmi_version *info;
int i;
for (i = 0, info = device->version_list;
i < device->version_count;
i++, info++) {
if (info->type == type) {
*major = info->major;
*minor = info->minor;
return true;
}
}
return false;
}
bool qmi_device_has_service(struct qmi_device *device, uint8_t type)
{
struct qmi_version *info;
int i;
for (i = 0, info = device->version_list;
i < device->version_count;
i++, info++) {
if (info->type == type) {
return true;
}
}
return false;
}
struct discover_data {
struct discovery super;
struct qmi_device *device;
@@ -1177,7 +1239,7 @@ done:
device->version_count = count;
if (data->func)
data->func(count, list, data->user_data);
data->func(data->user_data);
__qmi_device_discovery_complete(data->device, &data->super);
}
@@ -1213,8 +1275,7 @@ static gboolean discover_reply(gpointer user_data)
}
if (data->func)
data->func(device->version_count,
device->version_list, data->user_data);
data->func(data->user_data);
__qmi_device_discovery_complete(data->device, &data->super);
__request_free(req, NULL);
@@ -1227,7 +1288,7 @@ bool qmi_device_discover(struct qmi_device *device, qmi_discover_func_t func,
{
struct discover_data *data;
struct qmi_request *req;
struct qmi_control_hdr *hdr;
uint8_t tid;
if (!device)
return false;
@@ -1251,21 +1312,12 @@ bool qmi_device_discover(struct qmi_device *device, qmi_discover_func_t func,
}
req = __request_alloc(QMI_SERVICE_CONTROL, 0x00,
QMI_CTL_GET_VERSION_INFO, QMI_CONTROL_HDR_SIZE,
NULL, 0, discover_callback, data, (void **) &hdr);
if (!req) {
g_free(data);
return false;
}
QMI_CTL_GET_VERSION_INFO,
NULL, 0, discover_callback, data);
if (device->next_control_tid < 1)
device->next_control_tid = 1;
tid = __request_submit(device, req);
hdr->type = 0x00;
hdr->transaction = device->next_control_tid++;
data->tid = hdr->transaction;
__request_submit(device, req, hdr->transaction);
data->tid = tid;
data->timeout = g_timeout_add_seconds(5, discover_reply, data);
__qmi_device_discovery_started(device, &data->super);
@@ -1279,24 +1331,13 @@ static void release_client(struct qmi_device *device,
{
unsigned char release_req[] = { 0x01, 0x02, 0x00, type, client_id };
struct qmi_request *req;
struct qmi_control_hdr *hdr;
req = __request_alloc(QMI_SERVICE_CONTROL, 0x00,
QMI_CTL_RELEASE_CLIENT_ID, QMI_CONTROL_HDR_SIZE,
QMI_CTL_RELEASE_CLIENT_ID,
release_req, sizeof(release_req),
func, user_data, (void **) &hdr);
if (!req) {
func(0x0000, 0x0000, NULL, user_data);
return;
}
func, user_data);
if (device->next_control_tid < 1)
device->next_control_tid = 1;
hdr->type = 0x00;
hdr->transaction = device->next_control_tid++;
__request_submit(device, req, hdr->transaction);
__request_submit(device, req);
}
static void shutdown_destroy(gpointer user_data)
@@ -1374,7 +1415,6 @@ bool qmi_device_sync(struct qmi_device *device,
qmi_sync_func_t func, void *user_data)
{
struct qmi_request *req;
struct qmi_control_hdr *hdr;
struct sync_data *func_data;
if (!device)
@@ -1387,17 +1427,11 @@ bool qmi_device_sync(struct qmi_device *device,
func_data->user_data = user_data;
req = __request_alloc(QMI_SERVICE_CONTROL, 0x00,
QMI_CTL_SYNC, QMI_CONTROL_HDR_SIZE,
QMI_CTL_SYNC,
NULL, 0,
qmi_device_sync_callback, func_data, (void **) &hdr);
qmi_device_sync_callback, func_data);
if (device->next_control_tid < 1)
device->next_control_tid = 1;
hdr->type = 0x00;
hdr->transaction = device->next_control_tid++;
__request_submit(device, req, hdr->transaction);
__request_submit(device, req);
return true;
}
@@ -1898,7 +1932,6 @@ bool qmi_result_get_uint64(struct qmi_result *result, uint8_t type,
struct service_create_data {
struct discovery super;
struct qmi_device *device;
bool shared;
uint8_t type;
uint16_t major;
uint16_t minor;
@@ -1969,7 +2002,6 @@ static void service_create_callback(uint16_t message, uint16_t length,
service->ref_count = 1;
service->device = data->device;
service->shared = data->shared;
service->type = data->type;
service->major = data->major;
@@ -1992,100 +2024,52 @@ done:
__qmi_device_discovery_complete(data->device, &data->super);
}
static void service_create_discover(uint8_t count,
const struct qmi_version *list, void *user_data)
{
struct service_create_data *data = user_data;
struct qmi_device *device = data->device;
struct qmi_request *req;
struct qmi_control_hdr *hdr;
unsigned char client_req[] = { 0x01, 0x01, 0x00, data->type };
unsigned int i;
__debug_device(device, "service create [type=%d]", data->type);
for (i = 0; i < count; i++) {
if (list[i].type == data->type) {
data->major = list[i].major;
data->minor = list[i].minor;
break;
}
}
req = __request_alloc(QMI_SERVICE_CONTROL, 0x00,
QMI_CTL_GET_CLIENT_ID, QMI_CONTROL_HDR_SIZE,
client_req, sizeof(client_req),
service_create_callback, data, (void **) &hdr);
if (!req) {
if (data->timeout > 0)
g_source_remove(data->timeout);
data->timeout = g_timeout_add_seconds(0,
service_create_reply, data);
__qmi_device_discovery_started(device, &data->super);
return;
}
if (device->next_control_tid < 1)
device->next_control_tid = 1;
hdr->type = 0x00;
hdr->transaction = device->next_control_tid++;
__request_submit(device, req, hdr->transaction);
}
static bool service_create(struct qmi_device *device, bool shared,
static bool service_create(struct qmi_device *device,
uint8_t type, qmi_create_func_t func,
void *user_data, qmi_destroy_func_t destroy)
{
struct service_create_data *data;
unsigned char client_req[] = { 0x01, 0x01, 0x00, type };
struct qmi_request *req;
int i;
data = g_try_new0(struct service_create_data, 1);
if (!data)
return false;
if (!device->version_list)
return false;
data->super.destroy = service_create_data_free;
data->device = device;
data->shared = shared;
data->type = type;
data->func = func;
data->user_data = user_data;
data->destroy = destroy;
if (device->version_list) {
service_create_discover(device->version_count,
device->version_list, data);
goto done;
__debug_device(device, "service create [type=%d]", type);
for (i = 0; i < device->version_count; i++) {
if (device->version_list[i].type == data->type) {
data->major = device->version_list[i].major;
data->minor = device->version_list[i].minor;
break;
}
}
if (qmi_device_discover(device, service_create_discover, data, NULL))
goto done;
req = __request_alloc(QMI_SERVICE_CONTROL, 0x00,
QMI_CTL_GET_CLIENT_ID,
client_req, sizeof(client_req),
service_create_callback, data);
g_free(data);
__request_submit(device, req);
return false;
done:
data->timeout = g_timeout_add_seconds(8, service_create_reply, data);
__qmi_device_discovery_started(device, &data->super);
return true;
}
bool qmi_service_create(struct qmi_device *device,
uint8_t type, qmi_create_func_t func,
void *user_data, qmi_destroy_func_t destroy)
{
if (!device || !func)
return false;
if (type == QMI_SERVICE_CONTROL)
return false;
return service_create(device, false, type, func, user_data, destroy);
}
struct service_create_shared_data {
struct discovery super;
struct qmi_service *service;
@@ -2161,7 +2145,15 @@ bool qmi_service_create_shared(struct qmi_device *device,
return 0;
}
return service_create(device, true, type, func, user_data, destroy);
return service_create(device, type, func, user_data, destroy);
}
bool qmi_service_create(struct qmi_device *device,
uint8_t type, qmi_create_func_t func,
void *user_data, qmi_destroy_func_t destroy)
{
return qmi_service_create_shared(device, type, func,
user_data, destroy);
}
static void service_release_callback(uint16_t message, uint16_t length,
@@ -2238,8 +2230,6 @@ bool qmi_service_get_version(struct qmi_service *service,
}
struct service_send_data {
struct qmi_service *service;
struct qmi_param *param;
qmi_result_func_t func;
void *user_data;
qmi_destroy_func_t destroy;
@@ -2250,8 +2240,6 @@ static void service_send_free(struct service_send_data *data)
if (data->destroy)
data->destroy(data->user_data);
qmi_param_free(data->param);
g_free(data);
}
@@ -2292,7 +2280,7 @@ uint16_t qmi_service_send(struct qmi_service *service,
struct qmi_device *device;
struct service_send_data *data;
struct qmi_request *req;
struct qmi_service_hdr *hdr;
uint16_t tid;
if (!service)
return 0;
@@ -2308,31 +2296,21 @@ uint16_t qmi_service_send(struct qmi_service *service,
if (!data)
return 0;
data->service = service;
data->param = param;
data->func = func;
data->user_data = user_data;
data->destroy = destroy;
req = __request_alloc(service->type, service->client_id,
message, QMI_SERVICE_HDR_SIZE,
data->param ? data->param->data : NULL,
data->param ? data->param->length : 0,
service_send_callback, data, (void **) &hdr);
if (!req) {
g_free(data);
return 0;
}
message,
param ? param->data : NULL,
param ? param->length : 0,
service_send_callback, data);
if (device->next_service_tid < 256)
device->next_service_tid = 256;
qmi_param_free(param);
hdr->type = 0x00;
hdr->transaction = device->next_service_tid++;
tid = __request_submit(device, req);
__request_submit(device, req, hdr->transaction);
return hdr->transaction;
return tid;
}
bool qmi_service_cancel(struct qmi_service *service, uint16_t id)

View File

@@ -61,13 +61,6 @@ enum qmi_device_expected_data_format {
QMI_DEVICE_EXPECTED_DATA_FORMAT_RAW_IP,
};
struct qmi_version {
uint8_t type;
uint16_t major;
uint16_t minor;
const char *name;
};
void qmi_free(void *ptr);
typedef void (*qmi_destroy_func_t)(void *user_data);
@@ -78,8 +71,7 @@ struct qmi_device;
typedef void (*qmi_debug_func_t)(const char *str, void *user_data);
typedef void (*qmi_sync_func_t)(void *user_data);
typedef void (*qmi_shutdown_func_t)(void *user_data);
typedef void (*qmi_discover_func_t)(uint8_t count,
const struct qmi_version *list, void *user_data);
typedef void (*qmi_discover_func_t)(void *user_data);
struct qmi_device *qmi_device_new(int fd);
@@ -96,6 +88,10 @@ bool qmi_device_discover(struct qmi_device *device, qmi_discover_func_t func,
bool qmi_device_shutdown(struct qmi_device *device, qmi_shutdown_func_t func,
void *user_data, qmi_destroy_func_t destroy);
bool qmi_device_has_service(struct qmi_device *device, uint8_t type);
bool qmi_device_get_service_version(struct qmi_device *device, uint8_t type,
uint16_t *major, uint16_t *minor);
bool qmi_device_sync(struct qmi_device *device,
qmi_sync_func_t func, void *user_data);
bool qmi_device_is_sync_supported(struct qmi_device *device);

View File

@@ -493,8 +493,15 @@ static bool get_card_status(const struct qmi_uim_slot_info *slot,
case 0x03: /* PUK1 or PUK for UPIN is required */
sim_stat->passwd_state = OFONO_SIM_PASSWORD_SIM_PUK;
break;
case 0x00: /* Unknown */
case 0x01: /* Detected */
case 0x04: /* Personalization state must be checked. */
/* This is temporary, we could retry and get another result */
case 0x05: /* PIN1 blocked */
case 0x06: /* Illegal */
/*
* This could be temporary, we should retry and
* expect another result
*/
sim_stat->passwd_state = OFONO_SIM_PASSWORD_INVALID;
need_retry = true;
break;
@@ -557,7 +564,7 @@ static enum get_card_status_result handle_get_card_status_result(
index = GUINT16_FROM_LE(status->index_gw_pri);
if ((index & 0xff) == i && (index >> 8) == n) {
if ((index & 0xff) == n && (index >> 8) == i) {
if (get_card_status(slot, info1, info2,
sim_stat))
res = GET_CARD_STATUS_RESULT_TEMP_ERROR;
@@ -595,20 +602,32 @@ static void query_passwd_state_cb(struct qmi_result *result,
struct sim_status sim_stat;
enum get_card_status_result res;
struct cb_data *retry_cbd;
unsigned int i;
for (i = 0; i < OFONO_SIM_PASSWORD_INVALID; i++)
sim_stat.retries[i] = -1;
res = handle_get_card_status_result(result, &sim_stat);
switch (res) {
case GET_CARD_STATUS_RESULT_OK:
DBG("passwd state %d", sim_stat.passwd_state);
data->retry_count = 0;
CALLBACK_WITH_SUCCESS(cb, sim_stat.passwd_state, cbd->data);
if (sim_stat.passwd_state == OFONO_SIM_PASSWORD_INVALID) {
CALLBACK_WITH_FAILURE(cb, -1, cbd->data);
ofono_sim_inserted_notify(sim, FALSE);
} else
CALLBACK_WITH_SUCCESS(cb, sim_stat.passwd_state,
cbd->data);
break;
case GET_CARD_STATUS_RESULT_TEMP_ERROR:
data->retry_count++;
if (data->retry_count > MAX_RETRY_COUNT) {
DBG("Failed after %d attempts", data->retry_count);
DBG("Failed after %d attempts. Card state:%d",
data->retry_count,
sim_stat.card_state);
data->retry_count = 0;
CALLBACK_WITH_FAILURE(cb, -1, cbd->data);
ofono_sim_inserted_notify(sim, FALSE);
} else {
DBG("Retry command");
retry_cbd = cb_data_new(cb, cbd->data);
@@ -622,6 +641,7 @@ static void query_passwd_state_cb(struct qmi_result *result,
DBG("Command failed");
data->retry_count = 0;
CALLBACK_WITH_FAILURE(cb, -1, cbd->data);
ofono_sim_inserted_notify(sim, FALSE);
break;
}
}
@@ -650,9 +670,13 @@ static void query_pin_retries_cb(struct qmi_result *result, void *user_data)
struct cb_data *cbd = user_data;
ofono_sim_pin_retries_cb_t cb = cbd->cb;
struct sim_status sim_stat;
unsigned int i;
DBG("");
for (i = 0; i < OFONO_SIM_PASSWORD_INVALID; i++)
sim_stat.retries[i] = -1;
if (handle_get_card_status_result(result, &sim_stat) !=
GET_CARD_STATUS_RESULT_OK) {
CALLBACK_WITH_FAILURE(cb, NULL, cbd->data);

View File

@@ -251,6 +251,7 @@ static void qmi_ussd_request(struct ofono_ussd *ussd, int dcs,
qmi_ussd->dcs = QMI_USSD_DCS_ASCII;
qmi_ussd->length = len;
memcpy(qmi_ussd->data, utf8, utf8_len);
g_free(utf8);
param = qmi_param_new();
if (param == NULL)
@@ -265,7 +266,6 @@ static void qmi_ussd_request(struct ofono_ussd *ussd, int dcs,
qmi_param_free(param);
error:
g_free(utf8);
g_free(cbd);
CALLBACK_WITH_FAILURE(cb, data);
}

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2015-2018 Jolla Ltd.
* Copyright (C) 2015-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -18,8 +18,6 @@
#include "ril_util.h"
#include "ril_log.h"
#include "common.h"
/* See 3GPP 27.007 7.4 for possible values */
#define RIL_MAX_SERVICE_LENGTH 3

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2015-2017 Jolla Ltd.
* Copyright (C) 2015-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -17,7 +17,7 @@
#include "ril_util.h"
#include "ril_log.h"
#include "common.h"
#include <ofono/netreg.h>
struct ril_call_forward {
GRilIoQueue *q;

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2015-2017 Jolla Ltd.
* Copyright (C) 2015-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -17,8 +17,6 @@
#include "ril_util.h"
#include "ril_log.h"
#include "common.h"
struct ril_call_settings {
GRilIoQueue *q;
guint timer_id;

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2016-2020 Jolla Ltd.
* Copyright (C) 2016-2021 Jolla Ltd.
* Copyright (C) 2020 Open Mobile Platform LLC.
*
* This program is free software; you can redistribute it and/or modify
@@ -25,6 +25,7 @@
#include <grilio_parser.h>
#include <gutil_idlepool.h>
#include <gutil_macros.h>
#include <gutil_misc.h>
#define DEFAULT_UPDATE_RATE_MS (10000) /* 10 sec */
@@ -35,7 +36,8 @@ typedef struct ril_cell_info RilCellInfo;
struct ril_cell_info {
GObject object;
struct sailfish_cell_info info;
struct ofono_cell_info info;
struct ofono_cell **cells;
GRilIoChannel *io;
struct ril_radio *radio;
struct ril_sim_card *sim_card;
@@ -47,6 +49,7 @@ struct ril_cell_info {
gulong event_id;
guint query_id;
guint set_rate_id;
gboolean enabled;
};
enum ril_cell_info_signal {
@@ -58,26 +61,18 @@ enum ril_cell_info_signal {
static guint ril_cell_info_signals[SIGNAL_COUNT] = { 0 };
G_DEFINE_TYPE(RilCellInfo, ril_cell_info, G_TYPE_OBJECT)
#define RIL_CELL_INFO_TYPE (ril_cell_info_get_type())
#define RIL_CELL_INFO(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj),\
RIL_CELL_INFO_TYPE, RilCellInfo))
#define PARENT_TYPE G_TYPE_OBJECT
#define PARENT_CLASS ril_cell_info_parent_class
#define THIS_TYPE (ril_cell_info_get_type())
#define THIS(obj) (G_TYPE_CHECK_INSTANCE_CAST((obj), THIS_TYPE, RilCellInfo))
G_DEFINE_TYPE(RilCellInfo, ril_cell_info, PARENT_TYPE)
#define DBG_(self,fmt,args...) DBG("%s" fmt, (self)->log_prefix, ##args)
static inline void ril_cell_free(struct sailfish_cell *cell)
{
g_slice_free(struct sailfish_cell, cell);
}
static void ril_cell_free1(gpointer cell)
{
ril_cell_free(cell);
}
static const char *ril_cell_info_int_format(int value, const char *format)
{
if (value == SAILFISH_CELL_INVALID_VALUE) {
if (value == OFONO_CELL_INVALID_VALUE) {
return "";
} else {
static GUtilIdlePool *ril_cell_info_pool = NULL;
@@ -89,41 +84,56 @@ static const char *ril_cell_info_int_format(int value, const char *format)
}
}
static gboolean ril_cell_info_list_identical(GSList *l1, GSList *l2)
static gint ril_cell_info_list_sort_cb(gconstpointer a, gconstpointer b)
{
while (l1 && l2) {
if (memcmp(l1->data, l2->data, sizeof(struct sailfish_cell))) {
return FALSE;
}
l1 = l1->next;
l2 = l2->next;
}
return !l1 && !l2;
return ofono_cell_compare_location(*(struct ofono_cell **)a,
*(struct ofono_cell **)b);
}
static void ril_cell_info_update_cells(struct ril_cell_info *self, GSList *l)
static gboolean ril_cell_info_list_identical(const ofono_cell_ptr *l1,
const ofono_cell_ptr *l2)
{
if (!ril_cell_info_list_identical(self->info.cells, l)) {
g_slist_free_full(self->info.cells, ril_cell_free1);
self->info.cells = l;
if (l1 && l2) {
while (*l1 && *l2) {
if (memcmp(*l1, *l2, sizeof(struct ofono_cell))) {
return FALSE;
}
l1++;
l2++;
}
return !*l1 && !*l2;
} else {
return (!l1 || !*l1) && (!l2 || !*l2);
}
}
/* Takes ownership of GPtrArray */
static void ril_cell_info_update_cells(RilCellInfo *self, GPtrArray *l)
{
if (l && !ril_cell_info_list_identical(self->cells,
(struct ofono_cell **)l->pdata)) {
gutil_ptrv_free((void**)self->cells);
self->info.cells = self->cells = (struct ofono_cell **)
g_ptr_array_free(l, FALSE);
g_signal_emit(self, ril_cell_info_signals
[SIGNAL_CELLS_CHANGED], 0);
} else {
g_slist_free_full(l, ril_cell_free1);
} else if (l) {
g_ptr_array_set_free_func(l, g_free);
g_ptr_array_free(l, TRUE);
}
}
static struct sailfish_cell *ril_cell_info_parse_cell_gsm(GRilIoParser *rilp,
static struct ofono_cell *ril_cell_info_parse_cell_gsm(GRilIoParser *rilp,
guint version, gboolean registered)
{
struct sailfish_cell *cell = g_slice_new0(struct sailfish_cell);
struct sailfish_cell_info_gsm *gsm = &cell->info.gsm;
struct ofono_cell *cell = g_new0(struct ofono_cell, 1);
struct ofono_cell_info_gsm *gsm = &cell->info.gsm;
/* Optional RIL_CellIdentityGsm_v12 part */
gsm->arfcn = SAILFISH_CELL_INVALID_VALUE;
gsm->bsic = SAILFISH_CELL_INVALID_VALUE;
gsm->arfcn = OFONO_CELL_INVALID_VALUE;
gsm->bsic = OFONO_CELL_INVALID_VALUE;
/* Optional RIL_GSM_SignalStrength_v12 part */
gsm->timingAdvance = SAILFISH_CELL_INVALID_VALUE;
gsm->timingAdvance = OFONO_CELL_INVALID_VALUE;
/* RIL_CellIdentityGsm */
if (grilio_parser_get_int32(rilp, &gsm->mcc) &&
grilio_parser_get_int32(rilp, &gsm->mnc) &&
@@ -148,24 +158,24 @@ static struct sailfish_cell *ril_cell_info_parse_cell_gsm(GRilIoParser *rilp,
",strength=%d"),
ril_cell_info_int_format(gsm->bitErrorRate, ",err=%d"),
ril_cell_info_int_format(gsm->timingAdvance, ",t=%d"));
cell->type = SAILFISH_CELL_TYPE_GSM;
cell->type = OFONO_CELL_TYPE_GSM;
cell->registered = registered;
return cell;
}
ofono_error("failed to parse GSM cell info");
ril_cell_free(cell);
g_free(cell);
return NULL;
}
static struct sailfish_cell *ril_cell_info_parse_cell_wcdma(GRilIoParser *rilp,
static struct ofono_cell *ril_cell_info_parse_cell_wcdma(GRilIoParser *rilp,
guint version, gboolean registered)
{
struct sailfish_cell *cell = g_slice_new0(struct sailfish_cell);
struct sailfish_cell_info_wcdma *wcdma = &cell->info.wcdma;
struct ofono_cell *cell = g_new0(struct ofono_cell, 1);
struct ofono_cell_info_wcdma *wcdma = &cell->info.wcdma;
/* Optional RIL_CellIdentityWcdma_v12 part */
wcdma->uarfcn = SAILFISH_CELL_INVALID_VALUE;
wcdma->uarfcn = OFONO_CELL_INVALID_VALUE;
if (grilio_parser_get_int32(rilp, &wcdma->mcc) &&
grilio_parser_get_int32(rilp, &wcdma->mnc) &&
grilio_parser_get_int32(rilp, &wcdma->lac) &&
@@ -185,24 +195,24 @@ static struct sailfish_cell *ril_cell_info_parse_cell_wcdma(GRilIoParser *rilp,
",strength=%d"),
ril_cell_info_int_format(wcdma->bitErrorRate,
",err=%d"));
cell->type = SAILFISH_CELL_TYPE_WCDMA;
cell->type = OFONO_CELL_TYPE_WCDMA;
cell->registered = registered;
return cell;
}
ofono_error("failed to parse WCDMA cell info");
ril_cell_free(cell);
g_free(cell);
return NULL;
}
static struct sailfish_cell *ril_cell_info_parse_cell_lte(GRilIoParser *rilp,
static struct ofono_cell *ril_cell_info_parse_cell_lte(GRilIoParser *rilp,
guint version, gboolean registered)
{
struct sailfish_cell *cell = g_slice_new0(struct sailfish_cell);
struct sailfish_cell_info_lte *lte = &cell->info.lte;
struct ofono_cell *cell = g_new0(struct ofono_cell, 1);
struct ofono_cell_info_lte *lte = &cell->info.lte;
/* Optional RIL_CellIdentityLte_v12 part */
lte->earfcn = SAILFISH_CELL_INVALID_VALUE;
lte->earfcn = OFONO_CELL_INVALID_VALUE;
if (grilio_parser_get_int32(rilp, &lte->mcc) &&
grilio_parser_get_int32(rilp, &lte->mnc) &&
grilio_parser_get_int32(rilp, &lte->ci) &&
@@ -229,18 +239,18 @@ static struct sailfish_cell *ril_cell_info_parse_cell_lte(GRilIoParser *rilp,
ril_cell_info_int_format(lte->rssnr, ",rssnr=%d"),
ril_cell_info_int_format(lte->cqi, ",cqi=%d"),
ril_cell_info_int_format(lte->timingAdvance, ",t=%d"));
cell->type = SAILFISH_CELL_TYPE_LTE;
cell->type = OFONO_CELL_TYPE_LTE;
cell->registered = registered;
return cell;
}
ofono_error("failed to parse LTE cell info");
ril_cell_free(cell);
g_free(cell);
return NULL;
}
static gboolean ril_cell_info_parse_cell(GRilIoParser *rilp, guint v,
struct sailfish_cell **cell_ptr)
struct ofono_cell **cell_ptr)
{
int type, reg;
@@ -249,7 +259,7 @@ static gboolean ril_cell_info_parse_cell(GRilIoParser *rilp, guint v,
/* Skip timestamp */
grilio_parser_get_int32_array(rilp, NULL, 3)) {
int skip = 0;
struct sailfish_cell *cell = NULL;
struct ofono_cell *cell = NULL;
/* Normalize the boolean value */
reg = (reg != FALSE);
@@ -290,23 +300,25 @@ static gboolean ril_cell_info_parse_cell(GRilIoParser *rilp, guint v,
return FALSE;
}
static GSList *ril_cell_info_parse_list(guint v, const void *data, guint len)
static GPtrArray *ril_cell_info_parse_list(guint v, const void *data, guint len)
{
GSList *l = NULL;
GPtrArray *l = NULL;
GRilIoParser rilp;
int i, n;
grilio_parser_init(&rilp, data, len);
if (grilio_parser_get_int32(&rilp, &n) && n > 0) {
struct sailfish_cell *c;
struct ofono_cell *c;
l = g_ptr_array_sized_new(n + 1);
DBG("%d cell(s):", n);
for (i=0; i<n && ril_cell_info_parse_cell(&rilp, v, &c); i++) {
if (c) {
l = g_slist_insert_sorted(l, c,
sailfish_cell_compare_func);
g_ptr_array_add(l, c);
}
}
g_ptr_array_sort(l, ril_cell_info_list_sort_cb);
g_ptr_array_add(l, NULL);
}
GASSERT(grilio_parser_at_end(&rilp));
@@ -316,7 +328,7 @@ static GSList *ril_cell_info_parse_list(guint v, const void *data, guint len)
static void ril_cell_info_list_changed_cb(GRilIoChannel *io, guint code,
const void *data, guint len, void *user_data)
{
struct ril_cell_info *self = RIL_CELL_INFO(user_data);
RilCellInfo *self = THIS(user_data);
DBG_(self, "");
ril_cell_info_update_cells(self, ril_cell_info_parse_list
@@ -326,38 +338,41 @@ static void ril_cell_info_list_changed_cb(GRilIoChannel *io, guint code,
static void ril_cell_info_list_cb(GRilIoChannel *io, int status,
const void *data, guint len, void *user_data)
{
struct ril_cell_info *self = RIL_CELL_INFO(user_data);
RilCellInfo *self = THIS(user_data);
DBG_(self, "");
GASSERT(self->query_id);
self->query_id = 0;
ril_cell_info_update_cells(self, (status == RIL_E_SUCCESS) ?
ril_cell_info_update_cells(self,
(status == RIL_E_SUCCESS && self->enabled) ?
ril_cell_info_parse_list(io->ril_version, data, len) : NULL);
}
static void ril_cell_info_set_rate_cb(GRilIoChannel *io, int status,
const void *data, guint len, void *user_data)
{
struct ril_cell_info *self = RIL_CELL_INFO(user_data);
RilCellInfo *self = THIS(user_data);
DBG_(self, "");
GASSERT(self->set_rate_id);
self->set_rate_id = 0;
}
static gboolean ril_cell_info_retry(GRilIoRequest* request, int ril_status,
const void* response_data, guint response_len, void* user_data)
static gboolean ril_cell_info_retry(GRilIoRequest *request, int ril_status,
const void *response_data, guint response_len, void *user_data)
{
RilCellInfo *self = THIS(user_data);
switch (ril_status) {
case RIL_E_SUCCESS:
case RIL_E_RADIO_NOT_AVAILABLE:
return FALSE;
default:
return TRUE;
return self->enabled;
}
}
static void ril_cell_info_query(struct ril_cell_info *self)
static void ril_cell_info_query(RilCellInfo *self)
{
GRilIoRequest *req = grilio_request_new();
@@ -370,10 +385,11 @@ static void ril_cell_info_query(struct ril_cell_info *self)
grilio_request_unref(req);
}
static void ril_cell_info_set_rate(struct ril_cell_info *self)
static void ril_cell_info_set_rate(RilCellInfo *self)
{
GRilIoRequest *req = grilio_request_array_int32_new(1,
(self->update_rate_ms >= 0) ? self->update_rate_ms : INT_MAX);
(self->update_rate_ms >= 0 && self->enabled) ?
self->update_rate_ms : INT_MAX);
grilio_request_set_retry(req, RIL_RETRY_MS, MAX_RETRIES);
grilio_request_set_retry_func(req, ril_cell_info_retry);
@@ -384,10 +400,11 @@ static void ril_cell_info_set_rate(struct ril_cell_info *self)
grilio_request_unref(req);
}
static void ril_cell_info_refresh(struct ril_cell_info *self)
static void ril_cell_info_refresh(RilCellInfo *self)
{
/* RIL_REQUEST_GET_CELL_INFO_LIST fails without SIM card */
if (self->radio->state == RADIO_STATE_ON && self->sim_card_ready) {
if (self->enabled && self->radio->state == RADIO_STATE_ON &&
self->sim_card_ready) {
ril_cell_info_query(self);
} else {
ril_cell_info_update_cells(self, NULL);
@@ -396,7 +413,7 @@ static void ril_cell_info_refresh(struct ril_cell_info *self)
static void ril_cell_info_radio_state_cb(struct ril_radio *radio, void *arg)
{
struct ril_cell_info *self = RIL_CELL_INFO(arg);
RilCellInfo *self = THIS(arg);
DBG_(self, "%s", ril_radio_state_to_string(radio->state));
ril_cell_info_refresh(self);
@@ -404,7 +421,7 @@ static void ril_cell_info_radio_state_cb(struct ril_radio *radio, void *arg)
static void ril_cell_info_sim_status_cb(struct ril_sim_card *sim, void *arg)
{
struct ril_cell_info *self = RIL_CELL_INFO(arg);
RilCellInfo *self = THIS(arg);
self->sim_card_ready = ril_sim_card_ready(sim);
DBG_(self, "%sready", self->sim_card_ready ? "" : "not ");
@@ -414,60 +431,57 @@ static void ril_cell_info_sim_status_cb(struct ril_sim_card *sim, void *arg)
}
}
/* sailfish_cell_info interface callbacks */
/* ofono_cell_info interface callbacks */
struct ril_cell_info_closure {
typedef struct ril_cell_info_closure {
GCClosure cclosure;
sailfish_cell_info_cb_t cb;
ofono_cell_info_cb_t cb;
void *arg;
};
} RilCellInfoClosure;
static inline struct ril_cell_info *ril_cell_info_cast
(struct sailfish_cell_info *info)
static inline RilCellInfo *ril_cell_info_cast(struct ofono_cell_info *info)
{
return G_CAST(info, struct ril_cell_info, info);
return G_CAST(info, RilCellInfo, info);
}
static void ril_cell_info_ref_proc(struct sailfish_cell_info *info)
static void ril_cell_info_ref_proc(struct ofono_cell_info *info)
{
g_object_ref(ril_cell_info_cast(info));
}
static void ril_cell_info_unref_proc(struct sailfish_cell_info *info)
static void ril_cell_info_unref_proc(struct ofono_cell_info *info)
{
g_object_unref(ril_cell_info_cast(info));
}
static void ril_cell_info_cells_changed_cb(struct ril_cell_info *self,
struct ril_cell_info_closure *closure)
static void ril_cell_info_cells_changed_cb(RilCellInfo *self,
RilCellInfoClosure *closure)
{
closure->cb(&self->info, closure->arg);
}
static gulong ril_cell_info_add_cells_changed_handler_proc
(struct sailfish_cell_info *info,
sailfish_cell_info_cb_t cb, void *arg)
(struct ofono_cell_info *info, ofono_cell_info_cb_t cb, void *arg)
{
if (cb) {
struct ril_cell_info_closure *closure =
(struct ril_cell_info_closure *) g_closure_new_simple
(sizeof(struct ril_cell_info_closure), NULL);
GCClosure* cc = &closure->cclosure;
RilCellInfoClosure *closure = (RilCellInfoClosure *)
g_closure_new_simple(sizeof(RilCellInfoClosure), NULL);
GCClosure *cc = &closure->cclosure;
cc->closure.data = closure;
cc->callback = G_CALLBACK(ril_cell_info_cells_changed_cb);
closure->cb = cb;
closure->arg = arg;
return g_signal_connect_closure_by_id(ril_cell_info_cast(info),
ril_cell_info_signals[SIGNAL_CELLS_CHANGED], 0,
&cc->closure, FALSE);
ril_cell_info_signals[SIGNAL_CELLS_CHANGED], 0,
&cc->closure, FALSE);
} else {
return 0;
}
}
static void ril_cell_info_remove_handler_proc(struct sailfish_cell_info *info,
gulong id)
static void ril_cell_info_remove_handler_proc(struct ofono_cell_info *info,
gulong id)
{
if (G_LIKELY(id)) {
g_signal_handler_disconnect(ril_cell_info_cast(info), id);
@@ -475,34 +489,40 @@ static void ril_cell_info_remove_handler_proc(struct sailfish_cell_info *info,
}
static void ril_cell_info_set_update_interval_proc
(struct sailfish_cell_info *info, int ms)
(struct ofono_cell_info *info, int ms)
{
struct ril_cell_info *self = ril_cell_info_cast(info);
RilCellInfo *self = ril_cell_info_cast(info);
if (self->update_rate_ms != ms) {
self->update_rate_ms = ms;
DBG_(self, "%d ms", ms);
if (self->enabled && self->sim_card_ready) {
ril_cell_info_set_rate(self);
}
}
}
void ril_cell_info_set_enabled_proc(struct ofono_cell_info *info,
gboolean enabled)
{
RilCellInfo *self = ril_cell_info_cast(info);
if (self->enabled != enabled) {
self->enabled = enabled;
DBG_(self, "%d", enabled);
ril_cell_info_refresh(self);
if (self->sim_card_ready) {
ril_cell_info_set_rate(self);
}
}
}
struct sailfish_cell_info *ril_cell_info_new(GRilIoChannel *io,
const char *log_prefix, struct ril_radio *radio,
struct ril_sim_card *sim_card)
struct ofono_cell_info *ril_cell_info_new(GRilIoChannel *io,
const char *log_prefix, struct ril_radio *radio,
struct ril_sim_card *sim_card)
{
static const struct sailfish_cell_info_proc ril_cell_info_proc = {
ril_cell_info_ref_proc,
ril_cell_info_unref_proc,
ril_cell_info_add_cells_changed_handler_proc,
ril_cell_info_remove_handler_proc,
ril_cell_info_set_update_interval_proc
};
RilCellInfo *self = g_object_new(THIS_TYPE, 0);
struct ril_cell_info *self = g_object_new(RIL_CELL_INFO_TYPE, 0);
self->info.proc = &ril_cell_info_proc;
self->io = grilio_channel_ref(io);
self->radio = ril_radio_ref(radio);
self->sim_card = ril_sim_card_ref(sim_card);
@@ -519,20 +539,34 @@ struct sailfish_cell_info *ril_cell_info_new(GRilIoChannel *io,
ril_cell_info_sim_status_cb, self);
self->sim_card_ready = ril_sim_card_ready(sim_card);
ril_cell_info_refresh(self);
/* Disable updates by default */
self->enabled = FALSE;
if (self->sim_card_ready) {
ril_cell_info_set_rate(self);
}
return &self->info;
}
static void ril_cell_info_init(struct ril_cell_info *self)
static void ril_cell_info_init(RilCellInfo *self)
{
static const struct ofono_cell_info_proc ril_cell_info_proc = {
ril_cell_info_ref_proc,
ril_cell_info_unref_proc,
ril_cell_info_add_cells_changed_handler_proc,
ril_cell_info_remove_handler_proc,
ril_cell_info_set_update_interval_proc,
ril_cell_info_set_enabled_proc
};
self->update_rate_ms = DEFAULT_UPDATE_RATE_MS;
self->info.cells = self->cells = g_new0(struct ofono_cell*, 1);
self->info.proc = &ril_cell_info_proc;
}
static void ril_cell_info_dispose(GObject *object)
{
struct ril_cell_info *self = RIL_CELL_INFO(object);
RilCellInfo *self = THIS(object);
grilio_channel_remove_handlers(self->io, &self->event_id, 1);
if (self->query_id) {
@@ -544,23 +578,25 @@ static void ril_cell_info_dispose(GObject *object)
FALSE);
self->set_rate_id = 0;
}
ril_radio_remove_handlers(self->radio, &self->radio_state_event_id, 1);
/* xxx_remove_handlers() zero the ids */
ril_radio_remove_handlers(self->radio,
&self->radio_state_event_id, 1);
ril_sim_card_remove_handlers(self->sim_card,
&self->sim_status_event_id, 1);
G_OBJECT_CLASS(ril_cell_info_parent_class)->dispose(object);
&self->sim_status_event_id, 1);
G_OBJECT_CLASS(PARENT_CLASS)->dispose(object);
}
static void ril_cell_info_finalize(GObject *object)
{
struct ril_cell_info *self = RIL_CELL_INFO(object);
RilCellInfo *self = THIS(object);
DBG_(self, "");
gutil_ptrv_free((void**)self->cells);
g_free(self->log_prefix);
grilio_channel_unref(self->io);
ril_radio_unref(self->radio);
ril_sim_card_unref(self->sim_card);
g_slist_free_full(self->info.cells, ril_cell_free1);
G_OBJECT_CLASS(ril_cell_info_parent_class)->finalize(object);
G_OBJECT_CLASS(PARENT_CLASS)->finalize(object);
}
static void ril_cell_info_class_init(RilCellInfoClass *klass)

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2016-2019 Jolla Ltd.
* Copyright (C) 2016-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -18,9 +18,9 @@
#include "ril_types.h"
#include <sailfish_cell_info.h>
#include <ofono/cell-info.h>
struct sailfish_cell_info *ril_cell_info_new(GRilIoChannel *io,
struct ofono_cell_info *ril_cell_info_new(GRilIoChannel *io,
const char *log_prefix, struct ril_radio *radio,
struct ril_sim_card *sim_card);

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2015-2020 Jolla Ltd.
* Copyright (C) 2015-2021 Jolla Ltd.
* Copyright (C) 2019-2020 Open Mobile Platform LLC.
*
* This program is free software; you can redistribute it and/or modify
@@ -28,234 +28,10 @@
/* Utilities for parsing ril_subscription.conf */
char *ril_config_get_string(GKeyFile *file, const char *group, const char *key)
{
char *val = g_key_file_get_string(file, group, key, NULL);
if (!val && strcmp(group, RILCONF_SETTINGS_GROUP)) {
/* Check the common section */
val = g_key_file_get_string(file, RILCONF_SETTINGS_GROUP, key,
NULL);
}
return val;
}
char **ril_config_get_strings(GKeyFile *file, const char *group,
const char *key, char delimiter)
{
char *str = ril_config_get_string(file, group, key);
if (str) {
char **strv, **p;
char delimiter_str[2];
delimiter_str[0] = delimiter;
delimiter_str[1] = 0;
strv = g_strsplit(str, delimiter_str, -1);
/* Strip whitespaces */
for (p = strv; *p; p++) {
*p = g_strstrip(*p);
}
g_free(str);
return strv;
}
return NULL;
}
gboolean ril_config_get_integer(GKeyFile *file, const char *group,
const char *key, int *out_value)
{
GError *error = NULL;
int value = g_key_file_get_integer(file, group, key, &error);
if (!error) {
if (out_value) {
*out_value = value;
}
return TRUE;
} else {
g_error_free(error);
if (strcmp(group, RILCONF_SETTINGS_GROUP)) {
/* Check the common section */
error = NULL;
value = g_key_file_get_integer(file,
RILCONF_SETTINGS_GROUP, key, &error);
if (!error) {
if (out_value) {
*out_value = value;
}
return TRUE;
}
g_error_free(error);
}
return FALSE;
}
}
gboolean ril_config_get_boolean(GKeyFile *file, const char *group,
const char *key, gboolean *out_value)
{
GError *error = NULL;
gboolean value = g_key_file_get_boolean(file, group, key, &error);
if (!error) {
if (out_value) {
*out_value = value;
}
return TRUE;
} else {
g_error_free(error);
if (strcmp(group, RILCONF_SETTINGS_GROUP)) {
/* Check the common section */
error = NULL;
value = g_key_file_get_boolean(file,
RILCONF_SETTINGS_GROUP, key, &error);
if (!error) {
if (out_value) {
*out_value = value;
}
return TRUE;
}
g_error_free(error);
}
return FALSE;
}
}
gboolean ril_config_get_flag(GKeyFile *file, const char *group,
const char *key, int flag, int *flags)
{
gboolean value;
if (ril_config_get_boolean(file, group, key, &value)) {
if (value) {
*flags |= flag;
} else {
*flags &= ~flag;
}
return TRUE;
} else {
return FALSE;
}
}
gboolean ril_config_get_enum(GKeyFile *file, const char *group,
const char *key, int *result,
const char *name, int value, ...)
{
char *str = ril_config_get_string(file, group, key);
if (str) {
/*
* Some people are thinking that # is a comment
* anywhere on the line, not just at the beginning
*/
char *comment = strchr(str, '#');
if (comment) *comment = 0;
g_strstrip(str);
if (strcasecmp(str, name)) {
va_list args;
va_start(args, value);
while ((name = va_arg(args, char*)) != NULL) {
value = va_arg(args, int);
if (!strcasecmp(str, name)) {
break;
}
}
va_end(args);
}
if (!name) {
ofono_error("Invalid %s config value (%s)", key, str);
}
g_free(str);
if (name) {
if (result) {
*result = value;
}
return TRUE;
}
}
return FALSE;
}
gboolean ril_config_get_mask(GKeyFile *file, const char *group,
const char *key, int *result,
const char *name, int value, ...)
{
char *str = ril_config_get_string(file, group, key);
gboolean ok = FALSE;
if (result) {
*result = 0;
}
if (str) {
/*
* Some people are thinking that # is a comment
* anywhere on the line, not just at the beginning
*/
char *comment = strchr(str, '#');
char **values, **ptr;
if (comment) *comment = 0;
values = g_strsplit(str, "+", -1);
for (ok = TRUE, ptr = values; *ptr && ok; ptr++) {
const char* found_str = NULL;
const char* s = g_strstrip(*ptr);
if (!strcasecmp(s, name)) {
found_str = name;
if (result) {
*result |= value;
}
} else {
va_list args;
const char* known;
va_start(args, value);
while ((known = va_arg(args, char*)) != NULL) {
const int bit = va_arg(args, int);
if (!strcasecmp(s, known)) {
found_str = known;
if (result) {
*result |= bit;
}
break;
}
}
va_end(args);
}
if (!found_str) {
ofono_error("Unknown bit '%s' in %s", s, key);
ok = FALSE;
}
}
g_strfreev(values);
g_free(str);
}
if (!ok && result) {
*result = 0;
}
return ok;
}
GUtilInts *ril_config_get_ints(GKeyFile *file, const char *group,
const char *key)
{
char *value = ril_config_get_string(file, group, key);
char *value = ofono_conf_get_string(file, group, key);
if (value) {
GUtilIntArray *array = gutil_int_array_new();

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2015-2020 Jolla Ltd.
* Copyright (C) 2015-2021 Jolla Ltd.
* Copyright (C) 2019-2020 Open Mobile Platform LLC.
*
* This program is free software; you can redistribute it and/or modify
@@ -19,28 +19,10 @@
#include "ril_types.h"
/* Utilities for parsing ril_subscription.conf */
#include <ofono/conf.h>
#define RILCONF_SETTINGS_GROUP "Settings"
#define RILCONF_SETTINGS_GROUP OFONO_COMMON_SETTINGS_GROUP
char *ril_config_get_string(GKeyFile *file, const char *group,
const char *key);
char **ril_config_get_strings(GKeyFile *file, const char *group,
const char *key, char delimiter);
gboolean ril_config_get_integer(GKeyFile *file, const char *group,
const char *key, int *value);
gboolean ril_config_get_boolean(GKeyFile *file, const char *group,
const char *key, gboolean *value);
gboolean ril_config_get_flag(GKeyFile *file, const char *group,
const char *key, int flag, int *flags);
gboolean ril_config_get_enum(GKeyFile *file, const char *group,
const char *key, int *result,
const char *name, int value, ...)
G_GNUC_NULL_TERMINATED;
gboolean ril_config_get_mask(GKeyFile *file, const char *group,
const char *key, int *result,
const char *name, int value, ...)
G_GNUC_NULL_TERMINATED;
GUtilInts *ril_config_get_ints(GKeyFile *file, const char *group,
const char *key);
char *ril_config_ints_to_string(GUtilInts *ints, char separator);

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2019 Jolla Ltd.
* Copyright (C) 2019-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -16,8 +16,7 @@
#include "ril_connman.h"
#include <ofono/log.h>
#include <gdbus.h>
#include <ofono/gdbus.h>
#include <gutil_macros.h>
#include <gutil_misc.h>

View File

@@ -31,8 +31,6 @@
#include <grilio_parser.h>
#include <grilio_request.h>
#include "common.h" /* ACCESS_TECHNOLOGY_EUTRAN */
/* Yes, it does sometimes take minutes in roaming */
#define SETUP_DATA_CALL_TIMEOUT (300*1000) /* ms */
@@ -898,7 +896,7 @@ static void ril_data_call_setup_cb(GRilIoChannel *io, int ril_status,
*/
case PDP_FAIL_MULTI_CONN_TO_SAME_PDN_NOT_ALLOWED:
if (priv->network->data.access_tech ==
ACCESS_TECHNOLOGY_EUTRAN &&
OFONO_ACCESS_TECHNOLOGY_EUTRAN &&
!priv->downgraded_tech) {
DBG("downgrading preferred technology");
priv->downgraded_tech = TRUE;
@@ -960,12 +958,6 @@ static gboolean ril_data_call_setup_submit(struct ril_data_request *req)
RADIO_TECH_LTE : priv->network->data.ril_tech;
if (tech > 2) {
tech += 2;
} else {
/*
* This value used to be hardcoded, let's keep using it
* as the default.
*/
tech = RADIO_TECH_HSPA;
}
if (setup->username && setup->username[0]) {

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2019 Jolla Ltd.
* Copyright (C) 2019-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -16,7 +16,7 @@
#include "ril_devmon.h"
struct ril_devmon_io *ril_devmon_start_io(struct ril_devmon *devmon,
GRilIoChannel *channel, struct sailfish_cell_info *cell_info)
GRilIoChannel *channel, struct ofono_cell_info *cell_info)
{
return devmon ? devmon->start_io(devmon, channel, cell_info) : NULL;
}

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2019-2020 Jolla Ltd.
* Copyright (C) 2019-2021 Jolla Ltd.
* Copyright (C) 2020 Open Mobile Platform LLC.
*
* This program is free software; you can redistribute it and/or modify
@@ -17,7 +17,9 @@
#ifndef RIL_DEVMON_H
#define RIL_DEVMON_H
#include "ril_cell_info.h"
#include "ril_types.h"
#include <ofono/cell-info.h>
/*
* Separate instance of ril_devmon is created for each modem.
@@ -31,7 +33,7 @@ struct ril_devmon_io {
struct ril_devmon {
void (*free)(struct ril_devmon *devmon);
struct ril_devmon_io *(*start_io)(struct ril_devmon *devmon,
GRilIoChannel *channel, struct sailfish_cell_info *cell_info);
GRilIoChannel *channel, struct ofono_cell_info *cell_info);
};
/*
@@ -65,7 +67,7 @@ struct ril_devmon *ril_devmon_combine(struct ril_devmon *devmon[], guint n);
/* Utilities (NULL tolerant) */
struct ril_devmon_io *ril_devmon_start_io(struct ril_devmon *devmon,
GRilIoChannel *channel, struct sailfish_cell_info *cell_info);
GRilIoChannel *channel, struct ofono_cell_info *cell_info);
void ril_devmon_io_free(struct ril_devmon_io *devmon_io);
void ril_devmon_free(struct ril_devmon *devmon);

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2019 Jolla Ltd.
* Copyright (C) 2019-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -31,7 +31,7 @@ static inline DevMon *ril_devmon_auto_cast(struct ril_devmon *pub)
}
static struct ril_devmon_io *ril_devmon_auto_start_io(struct ril_devmon *devmon,
GRilIoChannel *io, struct sailfish_cell_info *cell_info)
GRilIoChannel *io, struct ofono_cell_info *cell_info)
{
DevMon *self = ril_devmon_auto_cast(devmon);

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2020 Jolla Ltd.
* Copyright (C) 2020-2021 Jolla Ltd.
* Copyright (C) 2020 Open Mobile Platform LLC.
*
* This program is free software; you can redistribute it and/or modify
@@ -52,7 +52,7 @@ static void ril_devmon_combine_io_free(struct ril_devmon_io *io)
}
static struct ril_devmon_io *ril_devmon_combine_start_io(struct ril_devmon *dm,
GRilIoChannel *chan, struct sailfish_cell_info *ci)
GRilIoChannel *chan, struct ofono_cell_info *ci)
{
guint i;
DevMon *self = ril_devmon_combine_cast(dm);

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2019 Jolla Ltd.
* Copyright (C) 2019-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -72,7 +72,7 @@ typedef struct ril_devmon_ds {
typedef struct ril_devmon_ds_io {
struct ril_devmon_io pub;
struct ril_connman *connman;
struct sailfish_cell_info *cell_info;
struct ofono_cell_info *cell_info;
MceBattery *battery;
MceCharger *charger;
MceDisplay *display;
@@ -201,7 +201,7 @@ static void ril_devmon_ds_io_update_low_data(DevMonIo *self)
static void ril_devmon_ds_io_set_cell_info_update_interval(DevMonIo *self)
{
sailfish_cell_info_set_update_interval(self->cell_info,
ofono_cell_info_set_update_interval(self->cell_info,
(ril_devmon_ds_display_on(self->display) &&
(ril_devmon_ds_charging(self->charger) ||
ril_devmon_ds_battery_ok(self->battery))) ?
@@ -257,12 +257,12 @@ static void ril_devmon_ds_io_free(struct ril_devmon_io *devmon_io)
grilio_channel_cancel_request(self->io, self->charging_req_id, FALSE);
grilio_channel_unref(self->io);
sailfish_cell_info_unref(self->cell_info);
ofono_cell_info_unref(self->cell_info);
g_free(self);
}
static struct ril_devmon_io *ril_devmon_ds_start_io(struct ril_devmon *devmon,
GRilIoChannel *io, struct sailfish_cell_info *cell_info)
GRilIoChannel *io, struct ofono_cell_info *cell_info)
{
DevMon *ds = ril_devmon_ds_cast(devmon);
DevMonIo *self = g_new0(DevMonIo, 1);
@@ -271,7 +271,7 @@ static struct ril_devmon_io *ril_devmon_ds_start_io(struct ril_devmon *devmon,
self->low_data_supported = TRUE;
self->charging_supported = TRUE;
self->io = grilio_channel_ref(io);
self->cell_info = sailfish_cell_info_ref(cell_info);
self->cell_info = ofono_cell_info_ref(cell_info);
self->connman = ril_connman_ref(ds->connman);
self->connman_event_id[CONNMAN_EVENT_VALID] =

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2019 Jolla Ltd.
* Copyright (C) 2019-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -56,7 +56,7 @@ typedef struct ril_devmon_ss {
typedef struct ril_devmon_ss_io {
struct ril_devmon_io pub;
struct sailfish_cell_info *cell_info;
struct ofono_cell_info *cell_info;
MceBattery *battery;
MceCharger *charger;
MceDisplay *display;
@@ -131,7 +131,7 @@ static void ril_devmon_ss_io_send_screen_state(DevMonIo *self)
static void ril_devmon_ss_io_set_cell_info_update_interval(DevMonIo *self)
{
sailfish_cell_info_set_update_interval(self->cell_info,
ofono_cell_info_set_update_interval(self->cell_info,
(self->display_on && (ril_devmon_ss_charging(self->charger) ||
ril_devmon_ss_battery_ok(self->battery))) ?
self->cell_info_interval_short_ms :
@@ -176,12 +176,12 @@ static void ril_devmon_ss_io_free(struct ril_devmon_io *devmon_io)
grilio_channel_cancel_request(self->io, self->req_id, FALSE);
grilio_channel_unref(self->io);
sailfish_cell_info_unref(self->cell_info);
ofono_cell_info_unref(self->cell_info);
g_free(self);
}
static struct ril_devmon_io *ril_devmon_ss_start_io(struct ril_devmon *devmon,
GRilIoChannel *io, struct sailfish_cell_info *cell_info)
GRilIoChannel *io, struct ofono_cell_info *cell_info)
{
DevMon *ss = ril_devmon_ss_cast(devmon);
DevMonIo *self = g_new0(DevMonIo, 1);
@@ -189,7 +189,7 @@ static struct ril_devmon_io *ril_devmon_ss_start_io(struct ril_devmon *devmon,
self->pub.free = ril_devmon_ss_io_free;
self->screen_state_supported = TRUE;
self->io = grilio_channel_ref(io);
self->cell_info = sailfish_cell_info_ref(cell_info);
self->cell_info = ofono_cell_info_ref(cell_info);
self->battery = mce_battery_ref(ss->battery);
self->battery_event_id[BATTERY_EVENT_VALID] =

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2019 Jolla Ltd.
* Copyright (C) 2019-2021 Jolla Ltd.
* Copyright (C) 2020 Open Mobile Platform LLC
*
* This program is free software; you can redistribute it and/or modify
@@ -61,7 +61,7 @@ typedef struct ril_devmon_ur {
typedef struct ril_devmon_ur_io {
struct ril_devmon_io pub;
struct sailfish_cell_info *cell_info;
struct ofono_cell_info *cell_info;
MceBattery *battery;
MceCharger *charger;
MceDisplay *display;
@@ -137,7 +137,7 @@ static void ril_devmon_ur_io_set_unsol_response_filter(DevMonIo *self)
static void ril_devmon_ur_io_set_cell_info_update_interval(DevMonIo *self)
{
sailfish_cell_info_set_update_interval(self->cell_info,
ofono_cell_info_set_update_interval(self->cell_info,
(self->display_on && (ril_devmon_ur_charging(self->charger) ||
ril_devmon_ur_battery_ok(self->battery))) ?
self->cell_info_interval_short_ms :
@@ -182,12 +182,12 @@ static void ril_devmon_ur_io_free(struct ril_devmon_io *devmon_io)
grilio_channel_cancel_request(self->io, self->req_id, FALSE);
grilio_channel_unref(self->io);
sailfish_cell_info_unref(self->cell_info);
ofono_cell_info_unref(self->cell_info);
g_free(self);
}
static struct ril_devmon_io *ril_devmon_ur_start_io(struct ril_devmon *devmon,
GRilIoChannel *io, struct sailfish_cell_info *cell_info)
GRilIoChannel *io, struct ofono_cell_info *cell_info)
{
DevMon *ur = ril_devmon_ur_cast(devmon);
DevMonIo *self = g_new0(DevMonIo, 1);
@@ -195,7 +195,7 @@ static struct ril_devmon_io *ril_devmon_ur_start_io(struct ril_devmon *devmon,
self->pub.free = ril_devmon_ur_io_free;
self->unsol_filter_supported = TRUE;
self->io = grilio_channel_ref(io);
self->cell_info = sailfish_cell_info_ref(cell_info);
self->cell_info = ofono_cell_info_ref(cell_info);
self->battery = mce_battery_ref(ur->battery);
self->battery_event_id[BATTERY_EVENT_VALID] =

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2015-2016 Jolla Ltd.
* Copyright (C) 2015-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -15,11 +15,12 @@
#include "ril_plugin.h"
#include "ril_network.h"
#include "ril_netreg.h"
#include "ril_data.h"
#include "ril_util.h"
#include "ril_log.h"
#include "common.h"
#include <ofono/misc.h>
/*
* This module is the ofono_gprs_driver implementation for rilmodem.
@@ -47,7 +48,7 @@ struct ril_gprs {
GRilIoQueue *q;
gboolean attached;
int max_cids;
enum network_registration_status registration_status;
enum ofono_netreg_status registration_status;
guint register_id;
gulong network_event_id;
gulong data_event_id;
@@ -78,11 +79,11 @@ static struct ril_gprs_cbd *ril_gprs_cbd_new(struct ril_gprs *gd,
return cbd;
}
static enum network_registration_status ril_gprs_fix_registration_status(
struct ril_gprs *gd, enum network_registration_status status)
static enum ofono_netreg_status ril_gprs_fix_registration_status(
struct ril_gprs *gd, enum ofono_netreg_status status)
{
if (!ril_data_allowed(gd->data)) {
return NETWORK_REGISTRATION_STATUS_NOT_REGISTERED;
return OFONO_NETREG_STATUS_NOT_REGISTERED;
} else {
/* TODO: need a way to make sure that SPDI information has
* already been read from the SIM (i.e. sim_spdi_read_cb in
@@ -94,13 +95,13 @@ static enum network_registration_status ril_gprs_fix_registration_status(
static void ril_gprs_data_update_registration_state(struct ril_gprs *gd)
{
const enum network_registration_status status =
const enum ofono_netreg_status status =
ril_gprs_fix_registration_status(gd, gd->network->data.status);
if (gd->registration_status != status) {
ofono_info("data reg changed %d -> %d (%s), attached %d",
gd->registration_status, status,
registration_status_to_string(status),
ofono_netreg_status_to_string(status),
gd->attached);
gd->registration_status = status;
ofono_gprs_status_notify(gd->gprs, gd->registration_status);
@@ -188,12 +189,10 @@ static void ril_gprs_registration_status(struct ofono_gprs *gprs,
{
struct ril_gprs *gd = ril_gprs_get_data(gprs);
struct ofono_error error;
const enum network_registration_status status = gd->attached ?
gd->registration_status :
NETWORK_REGISTRATION_STATUS_NOT_REGISTERED;
const enum ofono_netreg_status status = gd->attached ?
gd->registration_status : OFONO_NETREG_STATUS_NOT_REGISTERED;
DBG("%d (%s)", status, registration_status_to_string(status));
DBG("%d (%s)", status, ofono_netreg_status_to_string(status));
cb(ril_error_ok(&error), status, data);
}

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2015-2019 Jolla Ltd.
* Copyright (C) 2015-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -15,21 +15,20 @@
#include "ril_plugin.h"
#include "ril_network.h"
#include "ril_netreg.h"
#include "ril_data.h"
#include "ril_util.h"
#include "ril_log.h"
#include <ofono/mtu-limit.h>
#include <gutil_strv.h>
#include <arpa/inet.h>
#include "ofono.h"
#include "common.h"
#include "mtu-watch.h"
#define CTX_ID_NONE ((unsigned int)(-1))
#define MAX_MTU 1280
#define MAX_MMS_MTU 1280
struct ril_gprs_context_call {
struct ril_data_request *req;
@@ -44,7 +43,7 @@ struct ril_gprs_context {
struct ril_data *data;
guint active_ctx_cid;
gulong calls_changed_id;
struct mtu_watch *mtu_watch;
struct ofono_mtu_limit *mtu_limit;
struct ril_data_call *active_call;
struct ril_gprs_context_call activate;
struct ril_gprs_context_call deactivate;
@@ -96,9 +95,9 @@ static void ril_gprs_context_free_active_call(struct ril_gprs_context *gcd)
ril_data_remove_handler(gcd->data, gcd->calls_changed_id);
gcd->calls_changed_id = 0;
}
if (gcd->mtu_watch) {
mtu_watch_free(gcd->mtu_watch);
gcd->mtu_watch = NULL;
if (gcd->mtu_limit) {
ofono_mtu_limit_free(gcd->mtu_limit);
gcd->mtu_limit = NULL;
}
}
@@ -108,10 +107,18 @@ static void ril_gprs_context_set_active_call(struct ril_gprs_context *gcd,
if (call) {
ril_data_call_free(gcd->active_call);
gcd->active_call = ril_data_call_dup(call);
if (!gcd->mtu_watch) {
gcd->mtu_watch = mtu_watch_new(MAX_MTU);
if (ofono_gprs_context_get_type(gcd->gc) ==
OFONO_GPRS_CONTEXT_TYPE_MMS) {
/*
* Some MMS providers have a problem with MTU
* greater than 1280. Let's be safe.
*/
if (!gcd->mtu_limit) {
gcd->mtu_limit =
ofono_mtu_limit_new(MAX_MMS_MTU);
}
}
mtu_watch_set_ifname(gcd->mtu_watch, call->ifname);
ofono_mtu_limit_set_ifname(gcd->mtu_limit, call->ifname);
ril_data_call_grab(gcd->data, call->cid, gcd);
} else {
ril_gprs_context_free_active_call(gcd);
@@ -247,34 +254,59 @@ static void ril_gprs_context_set_gateway(struct ofono_gprs_context *gc,
ofono_gprs_context_set_ipv6_gateway(gc, ipv6_gw);
}
static void ril_gprs_context_set_dns_servers(struct ofono_gprs_context *gc,
const struct ril_data_call *call)
typedef void (*ofono_gprs_context_list_setter_t)(struct ofono_gprs_context *gc,
const char **list);
static void ril_gprs_context_set_servers(struct ofono_gprs_context *gc,
char * const *list, ofono_gprs_context_list_setter_t set_ipv4,
ofono_gprs_context_list_setter_t set_ipv6)
{
int i;
char * const *list = call->dnses;
const char **ip_list = NULL, **ip_ptr = NULL;
const char **ipv6_list = NULL, **ipv6_ptr = NULL;
const int n = gutil_strv_length(list);
const char **ip_dns = g_new0(const char *, n+1);
const char **ipv6_dns = g_new0(const char *, n+1);
const char **ip_ptr = ip_dns;
const char **ipv6_ptr = ipv6_dns;
for (i = 0; i < n; i++) {
const char *addr = list[i];
switch (ril_gprs_context_address_family(addr)) {
case AF_INET:
if (!ip_ptr) {
ip_list = g_new0(const char *, n - i + 1);
ip_ptr = ip_list;
}
*ip_ptr++ = addr;
break;
case AF_INET6:
if (!ipv6_ptr) {
ipv6_list = g_new0(const char *, n - i + 1);
ipv6_ptr = ipv6_list;
}
*ipv6_ptr++ = addr;
break;
}
}
ofono_gprs_context_set_ipv4_dns_servers(gc, ip_dns);
ofono_gprs_context_set_ipv6_dns_servers(gc, ipv6_dns);
set_ipv4(gc, ip_list);
set_ipv6(gc, ipv6_list);
g_free(ip_dns);
g_free(ipv6_dns);
g_free(ip_list);
g_free(ipv6_list);
}
static void ril_gprs_context_set_dns_servers(struct ofono_gprs_context *gc,
const struct ril_data_call *call)
{
ril_gprs_context_set_servers(gc, call->dnses,
ofono_gprs_context_set_ipv4_dns_servers,
ofono_gprs_context_set_ipv6_dns_servers);
}
static void ril_gprs_context_set_proxy_cscf(struct ofono_gprs_context *gc,
const struct ril_data_call *call)
{
ril_gprs_context_set_servers(gc, call->pcscf,
ofono_gprs_context_set_ipv4_proxy_cscf,
ofono_gprs_context_set_ipv6_proxy_cscf);
}
/* Only compares the stuff that's important to us */
@@ -282,7 +314,8 @@ static void ril_gprs_context_set_dns_servers(struct ofono_gprs_context *gc,
#define DATA_CALL_ADDRESS_CHANGED (0x02)
#define DATA_CALL_GATEWAY_CHANGED (0x04)
#define DATA_CALL_DNS_CHANGED (0x08)
#define DATA_CALL_ALL_CHANGED (0x0f)
#define DATA_CALL_PCSCF_CHANGED (0x10)
#define DATA_CALL_ALL_CHANGED (0x1f)
static int ril_gprs_context_data_call_change(
const struct ril_data_call *c1,
const struct ril_data_call *c2)
@@ -308,6 +341,10 @@ static int ril_gprs_context_data_call_change(
changes |= DATA_CALL_DNS_CHANGED;
}
if (!gutil_strv_equal(c1->pcscf, c2->pcscf)) {
changes |= DATA_CALL_PCSCF_CHANGED;
}
return changes;
} else {
return DATA_CALL_ALL_CHANGED;
@@ -380,6 +417,11 @@ static void ril_gprs_context_call_list_changed(struct ril_data *data, void *arg)
ril_gprs_context_set_dns_servers(gc, call);
}
if (change & DATA_CALL_PCSCF_CHANGED) {
DBG("P-CSCF changed");
ril_gprs_context_set_proxy_cscf(gc, call);
}
ofono_gprs_context_signal_change(gc, gcd->active_ctx_cid);
ril_data_call_free(prev_call);
}
@@ -421,6 +463,7 @@ static void ril_gprs_context_activate_primary_cb(struct ril_data *data,
ril_gprs_context_set_address(gc, call);
ril_gprs_context_set_gateway(gc, call);
ril_gprs_context_set_dns_servers(gc, call);
ril_gprs_context_set_proxy_cscf(gc, call);
ril_error_init_ok(&error);
}
@@ -444,14 +487,14 @@ static void ril_gprs_context_activate_primary(struct ofono_gprs_context *gc,
{
struct ril_gprs_context *gcd = ril_gprs_context_get_data(gc);
struct ofono_netreg *netreg = ril_modem_ofono_netreg(gcd->modem);
const int rs = ofono_netreg_get_status(netreg);
const enum ofono_netreg_status rs = ofono_netreg_get_status(netreg);
/* Let's make sure that we aren't connecting when roaming not allowed */
if (rs == NETWORK_REGISTRATION_STATUS_ROAMING) {
if (rs == OFONO_NETREG_STATUS_ROAMING) {
struct ofono_gprs *gprs = ril_modem_ofono_gprs(gcd->modem);
if (!__ofono_gprs_get_roaming_allowed(gprs) &&
if (!ofono_gprs_get_roaming_allowed(gprs) &&
ril_netreg_check_if_really_roaming(netreg, rs) ==
NETWORK_REGISTRATION_STATUS_ROAMING) {
OFONO_NETREG_STATUS_ROAMING) {
struct ofono_error error;
ofono_info("Can't activate context %u (roaming)",
ctx->cid);
@@ -468,7 +511,7 @@ static void ril_gprs_context_activate_primary(struct ofono_gprs_context *gc,
gcd->activate.cb = cb;
gcd->activate.data = data;
gcd->activate.req = ril_data_call_setup(gcd->data, ctx,
__ofono_gprs_context_get_assigned_type(gc),
ofono_gprs_context_get_assigned_type(gc),
ril_gprs_context_activate_primary_cb, gcd);
}
@@ -580,7 +623,7 @@ static void ril_gprs_context_remove(struct ofono_gprs_context *gc)
ril_data_unref(gcd->data);
ril_network_unref(gcd->network);
ril_data_call_free(gcd->active_call);
mtu_watch_free(gcd->mtu_watch);
ofono_mtu_limit_free(gcd->mtu_limit);
g_free(gcd);
}

View File

@@ -25,8 +25,9 @@
#include "ril_util.h"
#include "ril_log.h"
#include "ofono.h"
#include <ofono/message-waiting.h>
#include <ofono/cell-info.h>
#include <ofono/sim-auth.h>
#include <ofono/watch.h>
#define ONLINE_TIMEOUT_SECS (15) /* 20 sec is hardcoded in ofono core */
@@ -91,40 +92,26 @@ static struct ril_modem_data *ril_modem_data_from_ofono(struct ofono_modem *o)
return md;
}
static void *ril_modem_get_atom_data(struct ril_modem *modem,
enum ofono_atom_type type)
struct ofono_sim *ril_modem_ofono_sim(struct ril_modem *m)
{
if (modem && modem->ofono) {
struct ofono_atom *atom =
__ofono_modem_find_atom(modem->ofono, type);
if (atom) {
return __ofono_atom_get_data(atom);
}
}
return NULL;
return (m && m->ofono) ? ofono_modem_get_sim(m->ofono) : NULL;
}
struct ofono_sim *ril_modem_ofono_sim(struct ril_modem *modem)
struct ofono_gprs *ril_modem_ofono_gprs(struct ril_modem *m)
{
return ril_modem_get_atom_data(modem, OFONO_ATOM_TYPE_SIM);
return (m && m->ofono) ? ofono_modem_get_gprs(m->ofono) : NULL;
}
struct ofono_gprs *ril_modem_ofono_gprs(struct ril_modem *modem)
struct ofono_netreg *ril_modem_ofono_netreg(struct ril_modem *m)
{
return ril_modem_get_atom_data(modem, OFONO_ATOM_TYPE_GPRS);
}
struct ofono_netreg *ril_modem_ofono_netreg(struct ril_modem *modem)
{
return ril_modem_get_atom_data(modem, OFONO_ATOM_TYPE_NETREG);
return (m && m->ofono) ? ofono_modem_get_netreg(m->ofono) : NULL;
}
static inline struct ofono_radio_settings *ril_modem_radio_settings(
struct ril_modem *modem)
{
return ril_modem_get_atom_data(modem, OFONO_ATOM_TYPE_RADIO_SETTINGS);
return (modem && modem->ofono) ?
ofono_modem_get_radio_settings(modem->ofono) : NULL;
}
void ril_modem_delete(struct ril_modem *md)
@@ -447,7 +434,7 @@ static void ril_modem_remove(struct ofono_modem *ofono)
ril_network_unref(modem->network);
ril_sim_card_unref(modem->sim_card);
ril_data_unref(modem->data);
sailfish_cell_info_unref(modem->cell_info);
ofono_cell_info_unref(modem->cell_info);
grilio_channel_unref(modem->io);
grilio_queue_cancel_all(md->q, FALSE);
grilio_queue_unref(md->q);
@@ -466,7 +453,7 @@ struct ril_modem *ril_modem_create(GRilIoChannel *io, const char *log_prefix,
struct ril_radio *radio, struct ril_network *network,
struct ril_sim_card *card, struct ril_data *data,
struct ril_sim_settings *settings, struct ril_vendor *vendor,
struct sailfish_cell_info *cell_info)
struct ofono_cell_info *cell_info)
{
/* Skip the slash from the path, it looks like "/ril_0" */
struct ofono_modem *ofono = ofono_modem_create(path + 1,
@@ -497,7 +484,7 @@ struct ril_modem *ril_modem_create(GRilIoChannel *io, const char *log_prefix,
modem->network = ril_network_ref(network);
modem->sim_card = ril_sim_card_ref(card);
modem->sim_settings = ril_sim_settings_ref(settings);
modem->cell_info = sailfish_cell_info_ref(cell_info);
modem->cell_info = ofono_cell_info_ref(cell_info);
modem->data = ril_data_ref(data);
modem->io = grilio_channel_ref(io);
md->q = grilio_queue_new(io);

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2016-2018 Jolla Ltd.
* Copyright (C) 2016-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -17,13 +17,12 @@
#include "ril_util.h"
#include "ril_log.h"
#include <sailfish_cell_info.h>
#include "ofono.h"
#include <ofono/sim-mnclength.h>
#include <ofono/cell-info.h>
struct ril_netmon {
struct ofono_netmon *netmon;
struct sailfish_cell_info *cell_info;
struct ofono_cell_info *cell_info;
guint register_id;
};
@@ -48,7 +47,9 @@ static void ril_netmon_format_mccmnc(char *s_mcc, char *s_mnc, int mcc, int mnc)
if (mcc >= 0 && mcc <= 999) {
snprintf(s_mcc, OFONO_MAX_MCC_LENGTH + 1, "%03d", mcc);
if (mnc >= 0 && mnc <= 999) {
const unsigned int mnclen = mnclength(mcc, mnc);
const int mnclen =
ofono_sim_mnclength_get_mnclength_mccmnc(mcc,
mnc);
const char *format[] = { "%d", "%02d", "%03d" };
const char *fmt = (mnclen > 0 &&
mnclen <= G_N_ELEMENTS(format)) ?
@@ -69,7 +70,7 @@ static void ril_netmon_notify_ofono(struct ofono_netmon *netmon,
/* Better not to push uninitialized data to the stack ... */
for (i = nparams; i < RIL_NETMON_MAX_OFONO_PARAMS; i++) {
params[i].type = OFONO_NETMON_INFO_INVALID;
params[i].value = SAILFISH_CELL_INVALID_VALUE;
params[i].value = OFONO_CELL_INVALID_VALUE;
}
ril_netmon_format_mccmnc(s_mcc, s_mnc, mcc, mnc);
@@ -88,36 +89,36 @@ static void ril_netmon_notify_ofono(struct ofono_netmon *netmon,
}
static void ril_netmon_notify_gsm(struct ofono_netmon *netmon,
const struct sailfish_cell_info_gsm *gsm)
const struct ofono_cell_info_gsm *gsm)
{
struct ril_netmon_ofono_param params[RIL_NETMON_MAX_OFONO_PARAMS];
int n = 0;
if (gsm->lac != SAILFISH_CELL_INVALID_VALUE) {
if (gsm->lac != OFONO_CELL_INVALID_VALUE) {
params[n].type = OFONO_NETMON_INFO_LAC;
params[n].value = gsm->lac;
n++;
}
if (gsm->cid != SAILFISH_CELL_INVALID_VALUE) {
if (gsm->cid != OFONO_CELL_INVALID_VALUE) {
params[n].type = OFONO_NETMON_INFO_CI;
params[n].value = gsm->cid;
n++;
}
if (gsm->arfcn != SAILFISH_CELL_INVALID_VALUE) {
if (gsm->arfcn != OFONO_CELL_INVALID_VALUE) {
params[n].type = OFONO_NETMON_INFO_ARFCN;
params[n].value = gsm->arfcn;
n++;
}
if (gsm->signalStrength != SAILFISH_CELL_INVALID_VALUE) {
if (gsm->signalStrength != OFONO_CELL_INVALID_VALUE) {
params[n].type = OFONO_NETMON_INFO_RSSI;
params[n].value = gsm->signalStrength;
n++;
}
if (gsm->bitErrorRate != SAILFISH_CELL_INVALID_VALUE) {
if (gsm->bitErrorRate != OFONO_CELL_INVALID_VALUE) {
params[n].type = OFONO_NETMON_INFO_BER;
params[n].value = gsm->bitErrorRate;
n++;
@@ -128,42 +129,42 @@ static void ril_netmon_notify_gsm(struct ofono_netmon *netmon,
}
static void ril_netmon_notify_wcdma(struct ofono_netmon *netmon,
const struct sailfish_cell_info_wcdma *wcdma)
const struct ofono_cell_info_wcdma *wcdma)
{
struct ril_netmon_ofono_param params[RIL_NETMON_MAX_OFONO_PARAMS];
int n = 0;
if (wcdma->lac != SAILFISH_CELL_INVALID_VALUE) {
if (wcdma->lac != OFONO_CELL_INVALID_VALUE) {
params[n].type = OFONO_NETMON_INFO_LAC;
params[n].value = wcdma->lac;
n++;
}
if (wcdma->cid != SAILFISH_CELL_INVALID_VALUE) {
if (wcdma->cid != OFONO_CELL_INVALID_VALUE) {
params[n].type = OFONO_NETMON_INFO_CI;
params[n].value = wcdma->cid;
n++;
}
if (wcdma->psc != SAILFISH_CELL_INVALID_VALUE) {
if (wcdma->psc != OFONO_CELL_INVALID_VALUE) {
params[n].type = OFONO_NETMON_INFO_PSC;
params[n].value = wcdma->psc;
n++;
}
if (wcdma->uarfcn != SAILFISH_CELL_INVALID_VALUE) {
if (wcdma->uarfcn != OFONO_CELL_INVALID_VALUE) {
params[n].type = OFONO_NETMON_INFO_ARFCN;
params[n].value = wcdma->uarfcn;
n++;
}
if (wcdma->signalStrength != SAILFISH_CELL_INVALID_VALUE) {
if (wcdma->signalStrength != OFONO_CELL_INVALID_VALUE) {
params[n].type = OFONO_NETMON_INFO_RSSI;
params[n].value = wcdma->signalStrength;
n++;
}
if (wcdma->bitErrorRate != SAILFISH_CELL_INVALID_VALUE) {
if (wcdma->bitErrorRate != OFONO_CELL_INVALID_VALUE) {
params[n].type = OFONO_NETMON_INFO_BER;
params[n].value = wcdma->bitErrorRate;
n++;
@@ -174,48 +175,48 @@ static void ril_netmon_notify_wcdma(struct ofono_netmon *netmon,
}
static void ril_netmon_notify_lte(struct ofono_netmon *netmon,
const struct sailfish_cell_info_lte *lte)
const struct ofono_cell_info_lte *lte)
{
struct ril_netmon_ofono_param params[RIL_NETMON_MAX_OFONO_PARAMS];
int n = 0;
if (lte->ci != SAILFISH_CELL_INVALID_VALUE) {
if (lte->ci != OFONO_CELL_INVALID_VALUE) {
params[n].type = OFONO_NETMON_INFO_CI;
params[n].value = lte->ci;
n++;
}
if (lte->earfcn != SAILFISH_CELL_INVALID_VALUE) {
if (lte->earfcn != OFONO_CELL_INVALID_VALUE) {
params[n].type = OFONO_NETMON_INFO_EARFCN;
params[n].value = lte->earfcn;
n++;
}
if (lte->signalStrength != SAILFISH_CELL_INVALID_VALUE) {
if (lte->signalStrength != OFONO_CELL_INVALID_VALUE) {
params[n].type = OFONO_NETMON_INFO_RSSI;
params[n].value = lte->signalStrength;
n++;
}
if (lte->rsrp != SAILFISH_CELL_INVALID_VALUE) {
if (lte->rsrp != OFONO_CELL_INVALID_VALUE) {
params[n].type = OFONO_NETMON_INFO_RSRQ;
params[n].value = lte->rsrp;
n++;
}
if (lte->rsrq != SAILFISH_CELL_INVALID_VALUE) {
if (lte->rsrq != OFONO_CELL_INVALID_VALUE) {
params[n].type = OFONO_NETMON_INFO_RSRP;
params[n].value = lte->rsrq;
n++;
}
if (lte->cqi != SAILFISH_CELL_INVALID_VALUE) {
if (lte->cqi != OFONO_CELL_INVALID_VALUE) {
params[n].type = OFONO_NETMON_INFO_CQI;
params[n].value = lte->cqi;
n++;
}
if (lte->timingAdvance != SAILFISH_CELL_INVALID_VALUE) {
if (lte->timingAdvance != OFONO_CELL_INVALID_VALUE) {
params[n].type = OFONO_NETMON_INFO_TIMING_ADVANCE;
params[n].value = lte->timingAdvance;
n++;
@@ -229,28 +230,32 @@ static void ril_netmon_request_update(struct ofono_netmon *netmon,
ofono_netmon_cb_t cb, void *data)
{
struct ril_netmon *nm = ril_netmon_get_data(netmon);
const ofono_cell_ptr *cells = nm->cell_info->cells;
struct ofono_error error;
GSList *l;
for (l = nm->cell_info->cells; l; l = l->next) {
const struct sailfish_cell *cell = l->data;
if (cells) {
const ofono_cell_ptr *ptr;
if (cell->registered) {
switch (cell->type) {
case SAILFISH_CELL_TYPE_GSM:
ril_netmon_notify_gsm(netmon,
&cell->info.gsm);
break;
case SAILFISH_CELL_TYPE_WCDMA:
ril_netmon_notify_wcdma(netmon,
&cell->info.wcdma);
break;
case SAILFISH_CELL_TYPE_LTE:
ril_netmon_notify_lte(netmon,
&cell->info.lte);
break;
default:
break;
for (ptr = cells; *ptr; ptr++) {
const struct ofono_cell *cell = *ptr;
if (cell->registered) {
switch (cell->type) {
case OFONO_CELL_TYPE_GSM:
ril_netmon_notify_gsm(netmon,
&cell->info.gsm);
break;
case OFONO_CELL_TYPE_WCDMA:
ril_netmon_notify_wcdma(netmon,
&cell->info.wcdma);
break;
case OFONO_CELL_TYPE_LTE:
ril_netmon_notify_lte(netmon,
&cell->info.lte);
break;
default:
break;
}
}
}
}
@@ -278,7 +283,7 @@ static int ril_netmon_probe(struct ofono_netmon *netmon, unsigned int vendor,
if (modem->cell_info) {
struct ril_netmon *nm = g_slice_new0(struct ril_netmon);
nm->cell_info = sailfish_cell_info_ref(modem->cell_info);
nm->cell_info = ofono_cell_info_ref(modem->cell_info);
nm->netmon = netmon;
ofono_netmon_set_data(netmon, nm);
@@ -304,7 +309,7 @@ static void ril_netmon_remove(struct ofono_netmon *netmon)
g_source_remove(nm->register_id);
}
sailfish_cell_info_unref(nm->cell_info);
ofono_cell_info_unref(nm->cell_info);
g_slice_free(struct ril_netmon, nm);
}

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2015-2020 Jolla Ltd.
* Copyright (C) 2015-2021 Jolla Ltd.
* Copyright (C) 2019-2020 Open Mobile Platform LLC.
*
* This program is free software; you can redistribute it and/or modify
@@ -16,15 +16,13 @@
#include "ril_plugin.h"
#include "ril_network.h"
#include "ril_netreg.h"
#include "ril_util.h"
#include "ril_vendor.h"
#include "ril_log.h"
#include "ofono.h"
#include "common.h"
#include "simutil.h"
#include <ofono/watch.h>
#include <ofono/gprs-provision.h>
#define REGISTRATION_MAX_RETRIES (2)
@@ -93,20 +91,17 @@ static struct ril_netreg_cbd *ril_netreg_cbd_new(struct ril_netreg *nd,
return cbd;
}
int ril_netreg_check_if_really_roaming(struct ofono_netreg *netreg,
gint status)
enum ofono_netreg_status ril_netreg_check_if_really_roaming
(struct ofono_netreg *netreg, enum ofono_netreg_status status)
{
if (status == NETWORK_REGISTRATION_STATUS_ROAMING) {
if (status == OFONO_NETREG_STATUS_ROAMING) {
/* These functions tolerate NULL argument */
const char *net_mcc = ofono_netreg_get_mcc(netreg);
const char *net_mnc = ofono_netreg_get_mnc(netreg);
struct sim_spdi *spdi = ofono_netreg_get_spdi(netreg);
if (spdi && net_mcc && net_mnc) {
if (sim_spdi_lookup(spdi, net_mcc, net_mnc)) {
ofono_info("not roaming based on spdi");
return NETWORK_REGISTRATION_STATUS_REGISTERED;
}
if (ofono_netreg_spdi_lookup(netreg, net_mcc, net_mnc)) {
ofono_info("not roaming based on spdi");
return OFONO_NETREG_STATUS_REGISTERED;
}
}
@@ -202,7 +197,7 @@ static gboolean ril_netreg_strange(const struct ofono_network_operator *op,
{
gsize mcclen;
if (sim && op->status != OPERATOR_STATUS_CURRENT) {
if (sim && op->status != OFONO_OPERATOR_STATUS_CURRENT) {
const char *spn = ofono_sim_get_spn(sim);
const char *mcc = ofono_sim_get_mcc(sim);
const char *mnc = ofono_sim_get_mnc(sim);
@@ -243,7 +238,7 @@ static void ril_netreg_process_operators(struct ril_netreg *nd,
int np = 0;
if (ril_netreg_strange(op, nd->watch->sim) &&
__ofono_gprs_provision_get_settings(op->mcc,
ofono_gprs_provision_get_settings(op->mcc,
op->mnc, NULL, &prov, &np)) {
/* Use the first entry */
if (np > 0 && prov->provider_name &&
@@ -253,7 +248,7 @@ static void ril_netreg_process_operators(struct ril_netreg *nd,
strncpy(op->name, prov->provider_name,
OFONO_MAX_OPERATOR_NAME_LENGTH);
}
__ofono_gprs_provision_free_settings(prov, np);
ofono_gprs_provision_free_settings(prov, np);
}
}
}
@@ -306,16 +301,15 @@ static void ril_netreg_list_operators_cb(GRilIoChannel *io, int status,
}
/* Set the proper status */
if (!status) {
op->status = OPERATOR_STATUS_UNKNOWN;
} else if (!strcmp(status, "available")) {
op->status = OPERATOR_STATUS_AVAILABLE;
} else if (!strcmp(status, "current")) {
op->status = OPERATOR_STATUS_CURRENT;
} else if (!strcmp(status, "forbidden")) {
op->status = OPERATOR_STATUS_FORBIDDEN;
} else {
op->status = OPERATOR_STATUS_UNKNOWN;
op->status = OFONO_OPERATOR_STATUS_UNKNOWN;
if (status) {
if (!strcmp(status, "available")) {
op->status = OFONO_OPERATOR_STATUS_AVAILABLE;
} else if (!strcmp(status, "current")) {
op->status = OFONO_OPERATOR_STATUS_CURRENT;
} else if (!strcmp(status, "forbidden")) {
op->status = OFONO_OPERATOR_STATUS_FORBIDDEN;
}
}
op->tech = -1;

View File

@@ -0,0 +1,34 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*/
#ifndef RIL_NETREG_H
#define RIL_NETREG_H
#include "ril_types.h"
#include <ofono/netreg.h>
enum ofono_netreg_status ril_netreg_check_if_really_roaming
(struct ofono_netreg *reg, enum ofono_netreg_status status);
#endif /* RIL_NETREG_H */
/*
* Local Variables:
* mode: C
* c-basic-offset: 8
* indent-tabs-mode: t
* End:
*/

View File

@@ -34,11 +34,9 @@
#include <ofono/netreg.h>
#include <ofono/watch.h>
#include <ofono/misc.h>
#include <ofono/gprs.h>
#include "ofono.h"
#include "common.h"
#define SET_PREF_MODE_HOLDOFF_SEC RIL_RETRY_SECS
typedef GObjectClass RilNetworkClass;
@@ -188,7 +186,7 @@ static void ril_network_stop_timer(struct ril_network *self,
static void ril_network_reset_state(struct ril_registration_state *reg)
{
memset(reg, 0, sizeof(*reg));
reg->status = NETWORK_REGISTRATION_STATUS_UNKNOWN;
reg->status = OFONO_NETREG_STATUS_NONE;
reg->access_tech = -1;
reg->ril_tech = -1;
reg->lac = -1;
@@ -274,10 +272,10 @@ static gboolean ril_network_parse_response(struct ril_network *self,
reg->access_tech = ril_parse_tech(stech, &reg->ril_tech);
DBG_(self, "%s,%s,%s,%d,%s,%s,%s",
registration_status_to_string(reg->status),
slac, sci, reg->ril_tech,
registration_tech_to_string(reg->access_tech),
sreason, smax);
ofono_netreg_status_to_string(reg->status),
slac, sci, reg->ril_tech,
ofono_access_technology_to_string(reg->access_tech),
sreason, smax);
g_free(sstatus);
g_free(slac);
@@ -343,7 +341,7 @@ static void ril_network_poll_operator_cb(GRilIoChannel *io, int req_status,
op.tech = -1;
if (ril_parse_mcc_mnc(numeric, &op)) {
if (op.tech < 0) op.tech = self->voice.access_tech;
op.status = OPERATOR_STATUS_CURRENT;
op.status = OFONO_OPERATOR_STATUS_CURRENT;
op.name[0] = 0;
if (lalpha) {
strncpy(op.name, lalpha, sizeof(op.name));
@@ -372,7 +370,8 @@ static void ril_network_poll_operator_cb(GRilIoChannel *io, int req_status,
"%s, mcc=%s, mnc=%s, %s",
lalpha, salpha, numeric,
op.name, op.mcc, op.mnc,
registration_tech_to_string(op.tech));
ofono_access_technology_to_string
(op.tech));
} else {
DBG_(self, "no operator");
}
@@ -539,8 +538,8 @@ enum ofono_radio_access_mode ril_network_max_supported_mode
struct ril_network_priv *priv = self->priv;
const struct ril_radio_caps *caps = priv->caps;
return caps ? __ofono_radio_access_max_mode(caps->supported_modes) :
__ofono_radio_access_max_mode(settings->techs);
return caps ? ofono_radio_access_max_mode(caps->supported_modes) :
ofono_radio_access_max_mode(settings->techs);
}
static enum ofono_radio_access_mode ril_network_actual_pref_mode

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2015-2020 Jolla Ltd.
* Copyright (C) 2015-2021 Jolla Ltd.
* Copyright (C) 2020 Open Mobile Platform LLC.
*
* This program is free software; you can redistribute it and/or modify
@@ -19,14 +19,16 @@
#include "ril_types.h"
#include <ofono/netreg.h>
#include <glib-object.h>
struct ofono_network_operator;
struct ril_radio_caps;
struct ril_registration_state {
int status; /* enum network_registration_status */
int access_tech; /* enum access_technology or -1 if none */
enum ofono_netreg_status status;
enum ofono_access_technology access_tech;
int ril_tech;
int max_calls;
int lac;

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2015-2020 Jolla Ltd.
* Copyright (C) 2015-2021 Jolla Ltd.
* Copyright (C) 2020 Open Mobile Platform LLC.
*
* This program is free software; you can redistribute it and/or modify
@@ -18,8 +18,9 @@
#include "ril_util.h"
#include "ril_log.h"
#include "gdbus.h"
#include "ofono.h"
#include <ofono/gdbus.h>
#include <ofono/dbus.h>
#include <ofono/dbus-access.h>
#define RIL_OEM_RAW_INTERFACE "org.ofono.OemRaw"
#define RIL_OEM_RAW_TIMEOUT (60*1000) /* 60 sec */
@@ -56,10 +57,10 @@ static void ril_oem_raw_send_cb(GRilIoChannel *io, int ril_status,
dbus_message_iter_close_container(&it, &array);
} else if (ril_status == GRILIO_STATUS_TIMEOUT) {
DBG("Timed out");
reply = __ofono_error_timed_out(msg);
reply = ofono_dbus_error_timed_out(msg);
} else {
DBG("Error %s", ril_error_to_string(ril_status));
reply = __ofono_error_failed(msg);
reply = ofono_dbus_error_failed(msg);
}
g_dbus_send_message(ofono_dbus_get_connection(), reply);
@@ -71,10 +72,10 @@ static DBusMessage *ril_oem_raw_send(DBusConnection *conn, DBusMessage *msg,
DBusMessageIter it;
struct ril_oem_raw *oem = user_data;
if (!__ofono_dbus_access_method_allowed(dbus_message_get_sender(msg),
if (!ofono_dbus_access_method_allowed(dbus_message_get_sender(msg),
OFONO_DBUS_ACCESS_INTF_OEMRAW,
OFONO_DBUS_ACCESS_OEMRAW_SEND, NULL)) {
return __ofono_error_access_denied(msg);
return ofono_dbus_error_access_denied(msg);
}
dbus_message_iter_init(msg, &it);
@@ -104,7 +105,7 @@ static DBusMessage *ril_oem_raw_send(DBusConnection *conn, DBusMessage *msg,
return NULL;
} else {
DBG_(oem, "Unexpected signature");
return __ofono_error_invalid_args(msg);
return ofono_dbus_error_invalid_args(msg);
}
}

View File

@@ -5,8 +5,7 @@
* Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
* Copyright (C) ST-Ericsson SA 2010.
* Copyright (C) 2008-2011 Intel Corporation. All rights reserved.
* Copyright (C) 2013-2016 Jolla Ltd
* Contact: Jussi Kangas <jussi.kangas@tieto.com>
* Copyright (C) 2013-2021 Jolla Ltd
* Copyright (C) 2014 Canonical Ltd
*
* This program is free software; you can redistribute it and/or modify
@@ -21,10 +20,9 @@
#include "ril_plugin.h"
#include <ofono.h>
#include "simutil.h"
#include "util.h"
#include <ofono/modem.h>
#include <ofono/misc.h>
#include <ofono/log.h>
#define CALLBACK_WITH_FAILURE(cb, args...) \
do { \
@@ -44,6 +42,8 @@
} while (0)
#define SIM_EFPBR_FILEID 0x4F30
#define SIM_EFADN_FILEID 0x6F3A
#define SIM_EFEXT1_FILEID 0x6F4A
#define UNUSED 0xFF
@@ -148,8 +148,7 @@ static gint comp_int(gconstpointer a, gconstpointer b)
return a_val - b_val;
}
static const struct pb_file_info *
ext1_info(const GSList *pb_files)
static const struct pb_file_info *ext1_info(const GSList *pb_files)
{
const GSList *l;
for (l = pb_files; l; l = l->next) {
@@ -170,7 +169,7 @@ static struct phonebook_entry *handle_adn(size_t len, const unsigned char *msg,
unsigned extension_record = UNUSED;
unsigned i, prefix;
char *number = NULL;
char *name = sim_string_to_utf8(msg, name_length);
char *name = ofono_sim_string_to_utf8(msg, name_length);
struct phonebook_entry *new_entry;
/* Length contains also TON & NPI */
@@ -245,7 +244,7 @@ static struct phonebook_entry *handle_adn(size_t len, const unsigned char *msg,
return new_entry;
end:
g_free(name);
ofono_sim_string_free(name);
g_free(number);
return NULL;
@@ -303,7 +302,7 @@ static void handle_sne(size_t len, const unsigned char *msg,
if (rec_data->set_by_iap)
len -= 2;
sne = sim_string_to_utf8(msg, len);
sne = ofono_sim_string_to_utf8(msg, len);
if (sne && *sne != '\0') {
struct phonebook_entry *entry;
@@ -312,19 +311,17 @@ static void handle_sne(size_t len, const unsigned char *msg,
GINT_TO_POINTER(rec_data->adn_idx));
if (entry) {
/* If one already exists, delete it */
if (entry->sne)
g_free(entry->sne);
ofono_sim_string_free(entry->sne);
DBG("Adding SNE %s to %d", sne, rec_data->adn_idx);
DBG("name %s", entry->name);
entry->sne = sne;
} else {
g_free(sne);
sne = NULL;
}
} else {
g_free(sne);
}
ofono_sim_string_free(sne);
}
static void handle_anr(size_t len,
@@ -418,33 +415,31 @@ static void handle_email(size_t len, const unsigned char *msg,
const struct record_to_read *rec_data)
{
char *email;
struct phonebook_entry *entry;
/* There are additional fields for type 2 files */
if (rec_data->set_by_iap)
len -= 2;
email = sim_string_to_utf8(msg, len);
if (email == NULL || *email == '\0') {
g_free(email);
return;
}
email = ofono_sim_string_to_utf8(msg, len);
entry = g_tree_lookup(ref->phonebook,
if (email && *email) {
struct phonebook_entry *entry;
entry = g_tree_lookup(ref->phonebook,
GINT_TO_POINTER(rec_data->adn_idx));
if (entry == NULL) {
g_free(email);
return;
if (entry) {
/* if one already exists, delete it */
ofono_sim_string_free(entry->email);
DBG("Adding email to entry %d", rec_data->adn_idx);
DBG("name %s", entry->name);
entry->email = email;
email = NULL;
}
}
/* if one already exists, delete it */
if (entry->email)
g_free(entry->email);
DBG("Adding email to entry %d", rec_data->adn_idx);
DBG("name %s", entry->name);
entry->email = email;
ofono_sim_string_free(email);
}
static void handle_ext1(size_t len, const unsigned char *msg,
@@ -571,11 +566,11 @@ static gboolean free_entry(gpointer key, gpointer value, gpointer data)
{
struct phonebook_entry *entry = value;
g_free(entry->name);
ofono_sim_string_free(entry->name);
ofono_sim_string_free(entry->email);
ofono_sim_string_free(entry->sne);
g_free(entry->number);
g_free(entry->email);
g_free(entry->anr);
g_free(entry->sne);
g_free(entry);
return FALSE;
@@ -1022,7 +1017,7 @@ static int ril_phonebook_probe(struct ofono_phonebook *pb,
if (pd == NULL)
return -ENOMEM;
pd->sim = __ofono_atom_find(OFONO_ATOM_TYPE_SIM, modem);
pd->sim = ofono_modem_get_sim(modem);
if (pd->sim == NULL)
return -ENOENT;

File diff suppressed because it is too large Load Diff

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2015-2019 Jolla Ltd.
* Copyright (C) 2015-2021 Jolla Ltd.
* Copyright (C) 2019 Open Mobile Platform LLC.
*
* This program is free software; you can redistribute it and/or modify
@@ -18,7 +18,6 @@
#define RIL_PLUGIN_H
#include "ril_types.h"
#include "sailfish_manager.h"
#include <ofono/modem.h>
#include <ofono/call-barring.h>
@@ -52,7 +51,7 @@ struct ril_modem {
const char *log_prefix;
const char *ecclist_file;
struct ofono_modem *ofono;
struct sailfish_cell_info *cell_info;
struct ofono_cell_info *cell_info;
struct ril_vendor *vendor;
struct ril_radio *radio;
struct ril_data *data;
@@ -73,7 +72,7 @@ struct ril_modem *ril_modem_create(GRilIoChannel *io, const char *log_prefix,
struct ril_radio *radio, struct ril_network *network,
struct ril_sim_card *card, struct ril_data *data,
struct ril_sim_settings *settings, struct ril_vendor *vendor,
struct sailfish_cell_info *cell_info);
struct ofono_cell_info *cell_info);
void ril_modem_delete(struct ril_modem *modem);
struct ofono_sim *ril_modem_ofono_sim(struct ril_modem *modem);
struct ofono_gprs *ril_modem_ofono_gprs(struct ril_modem *modem);
@@ -85,7 +84,6 @@ struct ofono_netreg *ril_modem_ofono_netreg(struct ril_modem *modem);
#define ril_modem_io(modem) ((modem)->io)
int ril_sim_app_type(struct ofono_sim *sim);
int ril_netreg_check_if_really_roaming(struct ofono_netreg *reg, gint status);
extern const struct ofono_call_barring_driver ril_call_barring_driver;
extern const struct ofono_call_forwarding_driver ril_call_forwarding_driver;

View File

@@ -18,14 +18,11 @@
#include "ril_util.h"
#include "ril_log.h"
#include <ofono/misc.h>
#include <ofono/watch.h>
#include <gutil_misc.h>
#include "simutil.h"
#include "util.h"
#include "ofono.h"
#define SIM_STATE_CHANGE_TIMEOUT_SECS (5)
#define FAC_LOCK_QUERY_TIMEOUT_SECS (10)
#define FAC_LOCK_QUERY_RETRIES (1)
@@ -351,7 +348,7 @@ static void ril_sim_append_path(struct ril_sim *sd, GRilIoRequest *req,
const int fileid, const guchar *path, const guint path_len)
{
const enum ril_app_type app_type = ril_sim_card_app_type(sd->card);
guchar db_path[6] = { 0x00 };
guchar db_path[OFONO_EF_PATH_BUFFER_SIZE] = { 0x00 };
char *hex_path = NULL;
int len;
@@ -359,16 +356,16 @@ static void ril_sim_append_path(struct ril_sim *sd, GRilIoRequest *req,
memcpy(db_path, path, path_len);
len = path_len;
} else if (app_type == RIL_APPTYPE_USIM) {
len = sim_ef_db_get_path_3g(fileid, db_path);
len = ofono_get_ef_path_3g(fileid, db_path);
} else if (app_type == RIL_APPTYPE_SIM) {
len = sim_ef_db_get_path_2g(fileid, db_path);
len = ofono_get_ef_path_2g(fileid, db_path);
} else {
ofono_error("Unsupported app type %d", app_type);
len = 0;
}
if (len > 0) {
hex_path = encode_hex(db_path, len, 0);
hex_path = ril_encode_hex(db_path, len);
grilio_request_append_utf8(req, hex_path);
DBG_(sd, "%s", hex_path);
g_free(hex_path);
@@ -393,17 +390,15 @@ static struct ril_sim_io_response *ril_sim_parse_io_response(const void *data,
if (grilio_parser_get_int32(&rilp, &sw1) &&
grilio_parser_get_int32(&rilp, &sw2)) {
char *hex_data = grilio_parser_get_utf8(&rilp);
char *hex = grilio_parser_get_utf8(&rilp);
DBG("sw1=0x%02X,sw2=0x%02X,%s", sw1, sw2, hex_data);
DBG("sw1=0x%02X,sw2=0x%02X,%s", sw1, sw2, hex);
res = g_slice_new0(struct ril_sim_io_response);
res->sw1 = sw1;
res->sw2 = sw2;
if (hex_data) {
long num_bytes = 0;
res->data = decode_hex(hex_data, -1, &num_bytes, 0);
res->data_len = num_bytes;
g_free(hex_data);
if (hex) {
res->data = ril_decode_hex(hex, -1, &res->data_len);
g_free(hex);
}
}
@@ -509,15 +504,15 @@ static void ril_sim_file_info_cb(GRilIoChannel *io, int status,
gboolean ok = FALSE;
guchar access[3] = { 0x00, 0x00, 0x00 };
guchar file_status = EF_STATUS_VALID;
int flen = 0, rlen = 0, str = 0;
unsigned int flen = 0, rlen = 0, str = 0;
if (res->data_len) {
if (res->data[0] == 0x62) {
ok = sim_parse_3g_get_response(res->data,
ok = ofono_parse_get_response_3g(res->data,
res->data_len, &flen, &rlen, &str,
access, NULL);
} else {
ok = sim_parse_2g_get_response(res->data,
ok = ofono_parse_get_response_2g(res->data,
res->data_len, &flen, &rlen, &str,
access, &file_status);
}
@@ -658,7 +653,8 @@ static void ril_sim_write(struct ofono_sim *sim, guint cmd, int fileid,
ofono_sim_write_cb_t cb, void *data)
{
struct ril_sim *sd = ril_sim_get_data(sim);
char *hex_data = encode_hex(value, length, 0);
char *hex_data = ril_encode_hex(value, length);
ril_sim_request_io(sd, cmd, fileid, p1, p2, length, hex_data, path,
path_len, ril_sim_write_cb, ril_sim_cbd_io_new(sd, cb, data));
g_free(hex_data);
@@ -1201,8 +1197,7 @@ static void ril_sim_pin_change_state_cb(GRilIoChannel *io, int ril_status,
ril_status, cbd->passwd_type, retry_count);
if (ril_status == RIL_E_SUCCESS && retry_count == 0) {
enum ofono_sim_password_type associated_pin =
__ofono_sim_puk2pin(type);
enum ofono_sim_password_type pin_type = ofono_sim_puk2pin(type);
/*
* If PIN/PUK request has succeeded, zero retry count
* makes no sense, we have to assume that it's unknown.
@@ -1210,9 +1205,9 @@ static void ril_sim_pin_change_state_cb(GRilIoChannel *io, int ril_status,
* it can't be queried it will remain unknown.
*/
sd->retries[type] = -1;
if (associated_pin != OFONO_SIM_PASSWORD_INVALID) {
if (pin_type != OFONO_SIM_PASSWORD_INVALID) {
/* Successful PUK requests affect PIN retry count */
sd->retries[associated_pin] = -1;
sd->retries[pin_type] = -1;
}
} else {
sd->retries[type] = retry_count;
@@ -1488,12 +1483,11 @@ static gboolean ril_sim_list_apps_cb(void *data)
for (i = 0; i < n; i++) {
const char *hex = status->apps[i].aid;
gsize hex_len = hex ? strlen(hex) : 0;
long aid_size;
guint8 aid[16];
if (hex_len >= 2 && hex_len <= 2 * sizeof(aid) &&
!(hex_len & 0x01) && decode_hex_own_buf(hex,
hex_len, &aid_size, 0, aid)) {
gutil_hex2bin(hex, hex_len, aid)) {
const guint8 aid_size = (guint8)hex_len/2;
guint8 buf[4];
/*
@@ -1504,9 +1498,9 @@ static gboolean ril_sim_list_apps_cb(void *data)
* Application template TLV object.
*/
buf[0] = APP_TEMPLATE_TAG;
buf[1] = (guint8)(aid_size + 2);
buf[1] = aid_size + 2;
buf[2] = APP_ID_TAG;
buf[3] = (guint8)(aid_size);
buf[3] = aid_size;
g_byte_array_append(tlv, buf, sizeof(buf));
g_byte_array_append(tlv, aid, aid_size);
}
@@ -1570,7 +1564,7 @@ static void ril_sim_open_channel(struct ofono_sim *sim,
struct ril_sim *sd = ril_sim_get_data(sim);
struct ril_sim_cbd_io *cbd = ril_sim_cbd_io_new(sd, cb, data);
GRilIoRequest *req = grilio_request_new();
char *aid_hex = encode_hex(aid, len, 0);
char *aid_hex = ril_encode_hex(aid, len);
DBG_(sd, "%s", aid_hex);
grilio_request_append_utf8(req, aid_hex);
@@ -1713,7 +1707,7 @@ static void ril_sim_logical_access(struct ofono_sim *sim, int session_id,
GASSERT(len >= 5);
if (len > 5) {
hex_data = tmp = encode_hex(pdu + 5, len - 5, 0);
hex_data = tmp = ril_encode_hex(pdu + 5, len - 5);
} else {
tmp = NULL;
hex_data = "";
@@ -1768,7 +1762,7 @@ static void ril_sim_refresh_cb(GRilIoChannel *io, guint code,
* so we could be more descrete here. However I have't actually
* seen that in real life, let's just refresh everything for now.
*/
__ofono_sim_refresh(sd->sim, NULL, TRUE, TRUE);
ofono_sim_refresh_full(sd->sim);
}
static gboolean ril_sim_register(gpointer user)

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2015-2017 Jolla Ltd.
* Copyright (C) 2015-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -17,10 +17,6 @@
#include "ril_util.h"
#include "ril_log.h"
#include "smsutil.h"
#include "util.h"
#include "simutil.h"
#define RIL_SMS_ACK_RETRY_MS 1000
#define RIL_SMS_ACK_RETRY_COUNT 10
@@ -246,10 +242,10 @@ static void ril_sms_submit(struct ofono_sms *sms, const unsigned char *pdu,
/* TPDU:
*
* 'pdu' is a raw hexadecimal string
* encode_hex() turns it into an ASCII/hex UTF8 buffer
* ril_encode_hex() turns it into an ASCII/hex buffer (subset of utf8)
* grilio_request_append_utf8() encodes utf8 -> utf16
*/
tpdu = encode_hex(pdu + smsc_len, tpdu_len, 0);
tpdu = ril_encode_hex(pdu + smsc_len, tpdu_len);
grilio_request_append_utf8(req, tpdu);
DBG("%s", tpdu);
@@ -296,7 +292,7 @@ static void ril_sms_notify(GRilIoChannel *io, guint ril_event,
char *ril_pdu;
int ril_pdu_len;
unsigned int smsc_len;
long ril_buf_len;
guint ril_buf_len;
guchar *ril_data;
ril_pdu = NULL;
@@ -312,7 +308,7 @@ static void ril_sms_notify(GRilIoChannel *io, guint ril_event,
ril_pdu_len = strlen(ril_pdu);
DBG("ril_pdu_len is %d", ril_pdu_len);
ril_data = decode_hex(ril_pdu, ril_pdu_len, &ril_buf_len, -1);
ril_data = ril_decode_hex(ril_pdu, ril_pdu_len, &ril_buf_len);
if (ril_data == NULL)
goto error;
@@ -325,14 +321,16 @@ static void ril_sms_notify(GRilIoChannel *io, guint ril_event,
ofono_info("sms received, smsc_len is %d", smsc_len);
DBG("(%s)", ril_pdu);
if (ril_event == RIL_UNSOL_RESPONSE_NEW_SMS) {
/* Last parameter is 'tpdu_len' ( substract SMSC length ) */
ofono_sms_deliver_notify(sd->sms, ril_data, ril_buf_len,
if (ril_buf_len >= smsc_len) {
if (ril_event == RIL_UNSOL_RESPONSE_NEW_SMS) {
/* Last parameter is tpdu_len (substract SMSC length) */
ofono_sms_deliver_notify(sd->sms, ril_data, ril_buf_len,
ril_buf_len - smsc_len);
} else {
GASSERT(ril_event == RIL_UNSOL_RESPONSE_NEW_SMS_STATUS_REPORT);
ofono_sms_status_notify(sd->sms, ril_data, ril_buf_len,
} else {
/* RIL_UNSOL_RESPONSE_NEW_SMS_STATUS_REPORT */
ofono_sms_status_notify(sd->sms, ril_data, ril_buf_len,
ril_buf_len - smsc_len);
}
}
g_free(ril_pdu);

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2015-2017 Jolla Ltd.
* Copyright (C) 2015-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -17,8 +17,6 @@
#include "ril_util.h"
#include "ril_log.h"
#include "util.h"
#ifndef UI_LANG
# define UI_LANG "/var/lib/environment/nemo/locale.conf"
#endif
@@ -83,7 +81,7 @@ static void ril_stk_envelope(struct ofono_stk *stk, int length,
{
struct ril_stk *sd = ril_stk_get_data(stk);
GRilIoRequest *req = grilio_request_new();
char *hex_envelope = encode_hex(cmd, length, 0);
char *hex_envelope = ril_encode_hex(cmd, length);
DBG("%s", hex_envelope);
grilio_request_append_utf8(req, hex_envelope);
@@ -117,7 +115,7 @@ static void ril_stk_terminal_response(struct ofono_stk *stk, int length,
{
struct ril_stk *sd = ril_stk_get_data(stk);
GRilIoRequest *req = grilio_request_new();
char *hex_tr = encode_hex(resp, length, 0);
char *hex_tr = ril_encode_hex(resp, length);
DBG("rilmodem terminal response: %s", hex_tr);
grilio_request_append_utf8(req, hex_tr);
@@ -150,19 +148,21 @@ static void ril_stk_pcmd_notify(GRilIoChannel *io, guint code,
struct ril_stk *sd = user_data;
GRilIoParser rilp;
char *pcmd;
guchar *pdu;
long len = 0;
void *pdu;
guint len;
GASSERT(code == RIL_UNSOL_STK_PROACTIVE_COMMAND);
grilio_parser_init(&rilp, data, data_len);
pcmd = grilio_parser_get_utf8(&rilp);
DBG("pcmd: %s", pcmd);
pdu = decode_hex(pcmd, strlen(pcmd), &len, -1);
pdu = ril_decode_hex(pcmd, -1, &len);
if (pdu) {
DBG("pcmd: %s", pcmd);
ofono_stk_proactive_command_notify(sd->stk, len, pdu);
g_free(pdu);
} else {
ofono_warn("Failed to parse STK command %s", pcmd);
}
g_free(pcmd);
ofono_stk_proactive_command_notify(sd->stk, len, pdu);
g_free(pdu);
}
static void ril_stk_event_notify(GRilIoChannel *io, guint code,
@@ -170,20 +170,23 @@ static void ril_stk_event_notify(GRilIoChannel *io, guint code,
{
struct ril_stk *sd = user_data;
GRilIoParser rilp;
char *pcmd = NULL;
guchar *pdu = NULL;
long len;
char *pcmd;
void *pdu;
guint len;
/* Proactive command has been handled by the modem. */
GASSERT(code == RIL_UNSOL_STK_EVENT_NOTIFY);
grilio_parser_init(&rilp, data, data_len);
pcmd = grilio_parser_get_utf8(&rilp);
DBG("pcmd: %s", pcmd);
pdu = decode_hex(pcmd, strlen(pcmd), &len, -1);
pdu = ril_decode_hex(pcmd, -1, &len);
if (pdu) {
DBG("pcmd: %s", pcmd);
ofono_stk_proactive_command_handled_notify(sd->stk, len, pdu);
g_free(pdu);
} else {
ofono_warn("Failed to parse STK event %s", pcmd);
}
g_free(pcmd);
ofono_stk_proactive_command_handled_notify(sd->stk, len, pdu);
g_free(pdu);
}
static void ril_stk_session_end_notify(GRilIoChannel *io, guint code,

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2015-2020 Jolla Ltd.
* Copyright (C) 2015-2021 Jolla Ltd.
* Copyright (C) 2019-2020 Open Mobile Platform LLC.
*
* This program is free software; you can redistribute it and/or modify
@@ -83,6 +83,22 @@ struct ril_slot_config {
int cell_info_interval_long_ms;
};
/* Some values copied from ofono's internal common.h */
/* 27.007 Section 7.11 */
enum bearer_class {
BEARER_CLASS_VOICE = 1,
BEARER_CLASS_DATA = 2,
BEARER_CLASS_FAX = 4,
BEARER_CLASS_DEFAULT = 7,
BEARER_CLASS_SMS = 8,
BEARER_CLASS_DATA_SYNC = 16,
BEARER_CLASS_DATA_ASYNC = 32,
BEARER_CLASS_SS_DEFAULT = 61,
BEARER_CLASS_PACKET = 64,
BEARER_CLASS_PAD = 128
};
#endif /* RIL_TYPES_H */
/*

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2015-2019 Jolla Ltd.
* Copyright (C) 2015-2021 Jolla Ltd.
* Copyright (C) 2019 Open Mobile Platform LLC.
*
* This program is free software; you can redistribute it and/or modify
@@ -18,8 +18,7 @@
#include "ril_util.h"
#include "ril_log.h"
#include "smsutil.h"
#include "util.h"
#include <ofono/misc.h>
#define USSD_REQUEST_TIMEOUT_SEC (30)
#define USSD_CANCEL_TIMEOUT_SEC (20)
@@ -96,7 +95,7 @@ static void ril_ussd_request(struct ofono_ussd *ussd, int dcs,
const unsigned char *pdu, int len, ofono_ussd_cb_t cb, void *data)
{
struct ofono_error error;
enum sms_charset charset;
enum ofono_sms_charset charset;
struct ril_ussd *ud = ril_ussd_get_data(ussd);
ofono_info("send ussd, len:%d", len);
@@ -106,47 +105,42 @@ static void ril_ussd_request(struct ofono_ussd *ussd, int dcs,
ud->request_id = 0;
}
if (cbs_dcs_decode(dcs, NULL, NULL, &charset, NULL, NULL, NULL)) {
if (charset == SMS_CHARSET_7BIT) {
unsigned char unpacked_buf[182];
long written = 0;
if (ofono_decode_cbs_dcs_charset(dcs, &charset) &&
charset == OFONO_SMS_CHARSET_7BIT) {
char unpacked[182];
unsigned int written = ofono_unpack_7bit(pdu, len,
OFONO_UNPACK_7BIT_USSD, unpacked, sizeof(unpacked)-1);
unpack_7bit_own_buf(pdu, len, 0, TRUE,
sizeof(unpacked_buf)-1, &written, 0,
unpacked_buf);
unpacked[written] = 0;
if (written >= 1) {
/*
* When USSD was packed, additional CR
* might have been added (according to
* 23.038 6.1.2.3.1). So if the last
* character is CR, it should be removed
* here.
*
* Over 2 characters long USSD string must
* end with # (checked in valid_ussd_string),
* so it should be safe to remove extra CR.
*/
GRilIoRequest *req = grilio_request_new();
int length = strlen(unpacked);
unpacked_buf[written] = 0;
if (written >= 1) {
/*
* When USSD was packed, additional CR
* might have been added (according to
* 23.038 6.1.2.3.1). So if the last
* character is CR, it should be removed
* here.
*
* Over 2 characters long USSD string must
* end with # (checked in valid_ussd_string),
* so it should be safe to remove extra CR.
*/
GRilIoRequest *req = grilio_request_new();
int length = strlen((char *)unpacked_buf);
while (length > 2 &&
unpacked_buf[length-1] == '\r') {
unpacked_buf[--length] = 0;
}
grilio_request_append_utf8_chars(req, (char*)
unpacked_buf, length);
grilio_request_set_timeout(req,
USSD_REQUEST_TIMEOUT_SEC * 1000);
ud->request_id =
grilio_queue_send_request_full(ud->q,
req, RIL_REQUEST_SEND_USSD,
ril_ussd_response,
ril_ussd_cbd_free,
ril_ussd_cbd_new(ud, cb, data));
grilio_request_unref(req);
return;
while (length > 2 && unpacked[length-1] == '\r') {
unpacked[--length] = 0;
}
grilio_request_append_utf8_chars(req, (char*)
unpacked, length);
grilio_request_set_timeout(req,
USSD_REQUEST_TIMEOUT_SEC * 1000);
ud->request_id = grilio_queue_send_request_full(ud->q,
req, RIL_REQUEST_SEND_USSD,
ril_ussd_response,
ril_ussd_cbd_free,
ril_ussd_cbd_new(ud, cb, data));
grilio_request_unref(req);
return;
}
}

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2015-2019 Jolla Ltd.
* Copyright (C) 2015-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -20,12 +20,10 @@
#include <gutil_misc.h>
#include <sys/socket.h>
#include <ofono/netreg.h>
#include <ofono/misc.h>
#include <ctype.h>
#include "common.h"
#include "netreg.h"
#define RIL_PROTO_IP_STR "IP"
#define RIL_PROTO_IPV6_STR "IPV6"
#define RIL_PROTO_IPV4V6_STR "IPV4V6"
@@ -381,43 +379,43 @@ enum ril_auth ril_auth_method_from_ofono(enum ofono_gprs_auth_method auth)
return RIL_AUTH_BOTH;
}
/* Returns enum access_technology or -1 on failure. */
int ril_parse_tech(const char *stech, int *ril_tech)
enum ofono_access_technology ril_parse_tech(const char *stech, int *ril_tech)
{
int access_tech = -1;
int tech = -1;
enum ofono_access_technology access_tech =
OFONO_ACCESS_TECHNOLOGY_NONE;
if (gutil_parse_int(stech, 0, &tech)) {
switch (tech) {
case RADIO_TECH_GPRS:
case RADIO_TECH_GSM:
access_tech = ACCESS_TECHNOLOGY_GSM;
access_tech = OFONO_ACCESS_TECHNOLOGY_GSM;
break;
case RADIO_TECH_EDGE:
access_tech = ACCESS_TECHNOLOGY_GSM_EGPRS;
access_tech = OFONO_ACCESS_TECHNOLOGY_GSM_EGPRS;
break;
case RADIO_TECH_UMTS:
access_tech = ACCESS_TECHNOLOGY_UTRAN;
access_tech = OFONO_ACCESS_TECHNOLOGY_UTRAN;
break;
case RADIO_TECH_HSDPA:
access_tech = ACCESS_TECHNOLOGY_UTRAN_HSDPA;
access_tech = OFONO_ACCESS_TECHNOLOGY_UTRAN_HSDPA;
break;
case RADIO_TECH_HSUPA:
access_tech = ACCESS_TECHNOLOGY_UTRAN_HSUPA;
access_tech = OFONO_ACCESS_TECHNOLOGY_UTRAN_HSUPA;
break;
case RADIO_TECH_HSPA:
case RADIO_TECH_HSPAP:
access_tech = ACCESS_TECHNOLOGY_UTRAN_HSDPA_HSUPA;
access_tech = OFONO_ACCESS_TECHNOLOGY_UTRAN_HSDPA_HSUPA;
break;
case RADIO_TECH_LTE:
case RADIO_TECH_LTE_CA:
access_tech = ACCESS_TECHNOLOGY_EUTRAN;
access_tech = OFONO_ACCESS_TECHNOLOGY_EUTRAN;
break;
default:
DBG("Unknown RIL tech %s", stech);
/* no break */
case RADIO_TECH_IWLAN:
case RADIO_TECH_UNKNOWN:
tech = -1;
break;
}
@@ -472,6 +470,39 @@ gboolean ril_parse_mcc_mnc(const char *str, struct ofono_network_operator *op)
return FALSE;
}
char* ril_encode_hex(const void *in, guint size)
{
char *out = g_new(char, size * 2 + 1);
ofono_encode_hex(in, size, out);
return out;
}
void *ril_decode_hex(const char *hex, int len, guint *out_size)
{
void *out = NULL;
guint size = 0;
if (hex) {
if (len < 0) {
len = (int) strlen(hex);
}
if (len > 0 && !(len & 1)) {
size = len/2;
out = g_malloc(size);
if (!gutil_hex2bin(hex, len, out)) {
g_free(out);
out = NULL;
size = 0;
}
}
}
if (out_size) {
*out_size = size;
}
return out;
}
/*
* Local Variables:
* mode: C

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2015-2019 Jolla Ltd.
* Copyright (C) 2015-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -29,7 +29,7 @@ const char *ril_radio_state_to_string(int radio_state);
const char *ril_protocol_from_ofono(enum ofono_gprs_proto proto);
int ril_protocol_to_ofono(const char *str);
enum ril_auth ril_auth_method_from_ofono(enum ofono_gprs_auth_method auth);
int ril_parse_tech(const char *stech, int *ril_tech);
enum ofono_access_technology ril_parse_tech(const char *stech, int *ril_tech);
gboolean ril_parse_mcc_mnc(const char *str, struct ofono_network_operator *op);
#define ril_error_init_ok(err) \
@@ -43,6 +43,9 @@ gboolean ril_parse_mcc_mnc(const char *str, struct ofono_network_operator *op);
#define ril_error_failure(err) (ril_error_init_failure(err), err)
#define ril_error_sim(err,sw1,sw2) (ril_error_init_sim_error(err,sw1,sw2), err)
char *ril_encode_hex(const void *in, guint size);
void *ril_decode_hex(const char *hex, int len, guint *out_size);
#endif /* RIL_UTIL_H */
/*

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2015-2019 Jolla Ltd.
* Copyright (C) 2015-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -18,13 +18,13 @@
#include "ril_util.h"
#include "ril_log.h"
#include "common.h"
#include <gutil_ints.h>
#include <gutil_ring.h>
#include <gutil_idlequeue.h>
#include <gutil_intarray.h>
#include <ofono/misc.h>
#define FLAG_NEED_CLIP 1
#define VOICECALL_BLOCK_TIMEOUT_MS (5*1000)
@@ -138,7 +138,11 @@ static GSList *ril_voicecall_parse_clcc(const void *data, guint len)
gint tmp;
ofono_call_init(call);
grilio_parser_get_int32(&rilp, &call->status);
tmp = OFONO_CALL_STATUS_DISCONNECTED;
grilio_parser_get_int32(&rilp, &tmp);
call->status = tmp;
grilio_parser_get_uint32(&rilp, &call->id);
grilio_parser_get_int32(&rilp, &call->phone_number.type);
grilio_parser_get_int32(&rilp, NULL); /* isMpty */
@@ -146,8 +150,8 @@ static GSList *ril_voicecall_parse_clcc(const void *data, guint len)
tmp = 0;
grilio_parser_get_int32(&rilp, &tmp);
call->direction = (tmp ? /* isMT */
CALL_DIRECTION_MOBILE_TERMINATED :
CALL_DIRECTION_MOBILE_ORIGINATED);
OFONO_CALL_DIRECTION_MOBILE_TERMINATED :
OFONO_CALL_DIRECTION_MOBILE_ORIGINATED);
grilio_parser_get_int32(&rilp, NULL); /* als */
grilio_parser_get_int32(&rilp, &call->type); /* isVoice */
@@ -293,21 +297,21 @@ static void ril_voicecall_lastcause_cb(GRilIoChannel *io, int status,
case CALL_FAIL_NORMAL_UNSPECIFIED:
call_status = ril_voicecall_status_with_id(vc, id);
if (call_status == CALL_STATUS_ACTIVE ||
call_status == CALL_STATUS_HELD ||
call_status == CALL_STATUS_DIALING ||
call_status == CALL_STATUS_ALERTING) {
if (call_status == OFONO_CALL_STATUS_ACTIVE ||
call_status == OFONO_CALL_STATUS_HELD ||
call_status == OFONO_CALL_STATUS_DIALING ||
call_status == OFONO_CALL_STATUS_ALERTING) {
reason = OFONO_DISCONNECT_REASON_REMOTE_HANGUP;
} else if (call_status == CALL_STATUS_INCOMING) {
} else if (call_status == OFONO_CALL_STATUS_INCOMING) {
reason = OFONO_DISCONNECT_REASON_LOCAL_HANGUP;
}
break;
case CALL_FAIL_ERROR_UNSPECIFIED:
call_status = ril_voicecall_status_with_id(vc, id);
if (call_status == CALL_STATUS_DIALING ||
call_status == CALL_STATUS_ALERTING ||
call_status == CALL_STATUS_INCOMING) {
if (call_status == OFONO_CALL_STATUS_DIALING ||
call_status == OFONO_CALL_STATUS_ALERTING ||
call_status == OFONO_CALL_STATUS_INCOMING) {
reason = OFONO_DISCONNECT_REASON_REMOTE_HANGUP;
}
break;
@@ -420,7 +424,7 @@ static void ril_voicecall_clcc_poll_cb(GRilIoChannel *io, int status,
* arrives, or RING is used, then signal the call
* here
*/
if (nc->status == CALL_STATUS_INCOMING &&
if (nc->status == OFONO_CALL_STATUS_INCOMING &&
(vd->flags & FLAG_NEED_CLIP)) {
if (nc->type) {
ofono_voicecall_notify(vd->vc, nc);
@@ -548,7 +552,8 @@ static void ril_voicecall_dial(struct ofono_voicecall *vc,
void *data)
{
struct ril_voicecall *vd = ril_voicecall_get_data(vc);
const char *phstr = phone_number_to_string(ph);
char phbuf[OFONO_PHONE_NUMBER_BUFFER_SIZE];
const char *phstr = ofono_phone_number_to_string(ph, phbuf);
GRilIoRequest *req = grilio_request_new();
ofono_info("dialing \"%s\"", phstr);
@@ -631,14 +636,14 @@ static void ril_voicecall_hangup(struct ofono_voicecall *vc,
static gboolean ril_voicecall_hangup_active_filter(struct ofono_call *call)
{
switch (call->status) {
case CALL_STATUS_ACTIVE:
case CALL_STATUS_DIALING:
case CALL_STATUS_ALERTING:
case CALL_STATUS_INCOMING:
case OFONO_CALL_STATUS_ACTIVE:
case OFONO_CALL_STATUS_DIALING:
case OFONO_CALL_STATUS_ALERTING:
case OFONO_CALL_STATUS_INCOMING:
return TRUE;
case CALL_STATUS_HELD:
case CALL_STATUS_WAITING:
case CALL_STATUS_DISCONNECTED:
case OFONO_CALL_STATUS_HELD:
case OFONO_CALL_STATUS_WAITING:
case OFONO_CALL_STATUS_DISCONNECTED:
break;
}
return FALSE;

View File

@@ -38,6 +38,8 @@
#include <ofono/call-forwarding.h>
#include "common.h"
#pragma GCC diagnostic ignored "-Wrestrict"
#include "gril.h"
#include "rilmodem.h"

View File

@@ -108,7 +108,8 @@ static gboolean lte_delayed_register(gpointer user_data)
return FALSE;
}
static int ril_lte_probe(struct ofono_lte *lte, void *user_data)
static int ril_lte_probe(struct ofono_lte *lte,
unsigned int vendor, void *user_data)
{
GRil *ril = user_data;
struct ril_lte_data *ld;

View File

@@ -37,6 +37,8 @@
#include <ofono/modem.h>
#include <ofono/netreg.h>
#pragma GCC diagnostic ignored "-Wrestrict"
#include <gril/gril.h>
#include "common.h"

View File

@@ -91,7 +91,8 @@ static gboolean lte_delayed_register(gpointer user_data)
return FALSE;
}
static int ublox_lte_probe(struct ofono_lte *lte, void *data)
static int ublox_lte_probe(struct ofono_lte *lte,
unsigned int vendor, void *data)
{
GAtChat *chat = data;
struct lte_driver_data *ldd;

View File

@@ -30,6 +30,9 @@
#include <string.h>
#include <alloca.h>
#pragma GCC diagnostic ignored "-Wpragmas"
#pragma GCC diagnostic ignored "-Wcast-function-type"
#include <glib.h>
#include "ringbuffer.h"

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony
*
* Copyright (C) 2017-2019 Jolla Ltd.
* Copyright (C) 2017-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -13,20 +13,26 @@
* GNU General Public License for more details.
*/
#ifndef SAILFISH_CELL_INFO_H
#define SAILFISH_CELL_INFO_H
#ifndef OFONO_CELL_INFO_H
#define OFONO_CELL_INFO_H
#include <glib.h>
/* This API exists since mer/1.24+git2 */
enum sailfish_cell_type {
SAILFISH_CELL_TYPE_GSM,
SAILFISH_CELL_TYPE_WCDMA,
SAILFISH_CELL_TYPE_LTE
#ifdef __cplusplus
extern "C" {
#endif
#include <ofono/types.h>
enum ofono_cell_type {
OFONO_CELL_TYPE_GSM,
OFONO_CELL_TYPE_WCDMA,
OFONO_CELL_TYPE_LTE
};
#define SAILFISH_CELL_INVALID_VALUE (INT_MAX)
#define OFONO_CELL_INVALID_VALUE (INT_MAX)
struct sailfish_cell_info_gsm {
struct ofono_cell_info_gsm {
int mcc; /* Mobile Country Code (0..999) */
int mnc; /* Mobile Network Code (0..999) */
int lac; /* Location Area Code (0..65535) */
@@ -38,7 +44,7 @@ struct sailfish_cell_info_gsm {
int timingAdvance; /* Timing Advance. 1 period = 48/13 us */
};
struct sailfish_cell_info_wcdma {
struct ofono_cell_info_wcdma {
int mcc; /* Mobile Country Code (0..999) */
int mnc; /* Mobile Network Code (0..999) */
int lac; /* Location Area Code (0..65535) */
@@ -49,7 +55,7 @@ struct sailfish_cell_info_wcdma {
int bitErrorRate; /* (0-7, 99) TS 27.007 */
};
struct sailfish_cell_info_lte {
struct ofono_cell_info_lte {
int mcc; /* Mobile Country Code (0..999) */
int mnc; /* Mobile Network Code (0..999) */
int ci; /* Cell Identity */
@@ -64,51 +70,50 @@ struct sailfish_cell_info_lte {
int timingAdvance; /* (Distance = 300m/us) TS 36.321 */
};
struct sailfish_cell {
enum sailfish_cell_type type;
gboolean registered;
typedef struct ofono_cell {
enum ofono_cell_type type;
ofono_bool_t registered;
union {
struct sailfish_cell_info_gsm gsm;
struct sailfish_cell_info_wcdma wcdma;
struct sailfish_cell_info_lte lte;
struct ofono_cell_info_gsm gsm;
struct ofono_cell_info_wcdma wcdma;
struct ofono_cell_info_lte lte;
} info;
} *ofono_cell_ptr;
struct ofono_cell_info {
const struct ofono_cell_info_proc *proc;
const ofono_cell_ptr *cells; /* NULL-terminated */
};
struct sailfish_cell_info {
const struct sailfish_cell_info_proc *proc;
GSList *cells;
typedef void (*ofono_cell_info_cb_t)(struct ofono_cell_info *ci, void *data);
struct ofono_cell_info_proc {
void (*ref)(struct ofono_cell_info *ci);
void (*unref)(struct ofono_cell_info *ci);
unsigned long (*add_change_handler)(struct ofono_cell_info *ci,
ofono_cell_info_cb_t cb, void *data);
void (*remove_handler)(struct ofono_cell_info *ci, unsigned long id);
void (*set_update_interval)(struct ofono_cell_info *ci, int ms);
void (*set_enabled)(struct ofono_cell_info *ci, ofono_bool_t enabled);
};
typedef void (*sailfish_cell_info_cb_t)(struct sailfish_cell_info *info,
void *arg);
/* Wrappers for ofono_cell_info objects */
struct ofono_cell_info *ofono_cell_info_ref(struct ofono_cell_info *ci);
void ofono_cell_info_unref(struct ofono_cell_info *ci);
unsigned long ofono_cell_info_add_change_handler(struct ofono_cell_info *ci,
ofono_cell_info_cb_t cb, void *data);
void ofono_cell_info_remove_handler(struct ofono_cell_info *ci,
unsigned long id);
void ofono_cell_info_set_update_interval(struct ofono_cell_info *ci, int ms);
void ofono_cell_info_set_enabled(struct ofono_cell_info *ci, ofono_bool_t on);
int ofono_cell_compare_location(const struct ofono_cell *c1,
const struct ofono_cell *c2);
struct sailfish_cell_info_proc {
void (*ref)(struct sailfish_cell_info *info);
void (*unref)(struct sailfish_cell_info *info);
gulong (*add_cells_changed_handler)(struct sailfish_cell_info *info,
sailfish_cell_info_cb_t cb, void *arg);
void (*remove_handler)(struct sailfish_cell_info *info, gulong id);
void (*set_update_interval)(struct sailfish_cell_info *info, int ms);
};
#ifdef __cplusplus
}
#endif
/* Utilities */
gint sailfish_cell_compare_func(gconstpointer v1, gconstpointer v2);
gint sailfish_cell_compare_location(const struct sailfish_cell *c1,
const struct sailfish_cell *c2);
/* Cell info object API */
struct sailfish_cell_info *sailfish_cell_info_ref
(struct sailfish_cell_info *info);
void sailfish_cell_info_unref(struct sailfish_cell_info *info);
gulong sailfish_cell_info_add_cells_changed_handler
(struct sailfish_cell_info *info,
sailfish_cell_info_cb_t cb, void *arg);
void sailfish_cell_info_remove_handler(struct sailfish_cell_info *info,
gulong id);
void sailfish_cell_info_set_update_interval(struct sailfish_cell_info *info,
int ms);
#endif /* SAILFISH_CELINFO_H */
#endif /* OFONO_CELL_INFO_H */
/*
* Local Variables:

61
ofono/include/conf.h Normal file
View File

@@ -0,0 +1,61 @@
/*
* oFono - Open Source Telephony
*
* Copyright (C) 2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*/
#ifndef OFONO_CONF_H
#define OFONO_CONF_H
/* This API exists since mer/1.24+git2 */
#ifdef __cplusplus
extern "C" {
#endif
#include <glib.h>
/* If a value isn't found in the specified group, it's looked up in this one */
#define OFONO_COMMON_SETTINGS_GROUP "Settings"
/* Utilities for parsing config files */
void ofono_conf_merge_files(GKeyFile *conf, const char *file);
char *ofono_conf_get_string(GKeyFile *conf, const char *group,
const char *key) G_GNUC_WARN_UNUSED_RESULT;
char **ofono_conf_get_strings(GKeyFile *conf, const char *group,
const char *key, char delimiter) G_GNUC_WARN_UNUSED_RESULT;
gboolean ofono_conf_get_integer(GKeyFile *conf, const char *group,
const char *key, int *value);
gboolean ofono_conf_get_boolean(GKeyFile *conf, const char *group,
const char *key, gboolean *value);
gboolean ofono_conf_get_flag(GKeyFile *conf, const char *group,
const char *key, int flag, int *flags);
gboolean ofono_conf_get_enum(GKeyFile *conf, const char *group,
const char *key, int *result, const char *name, int value, ...)
G_GNUC_NULL_TERMINATED;
gboolean ofono_conf_get_mask(GKeyFile *conf, const char *group,
const char *key, int *result, const char *name, int value, ...)
G_GNUC_NULL_TERMINATED;
#ifdef __cplusplus
}
#endif
#endif /* OFONO_CONF_H */
/*
* Local Variables:
* mode: C
* c-basic-offset: 8
* indent-tabs-mode: t
* End:
*/

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony
*
* Copyright (C) 2019-2020 Jolla Ltd.
* Copyright (C) 2019-2021 Jolla Ltd.
* Copyright (C) 2020 Open Mobile Platform LLC.
*
* This program is free software; you can redistribute it and/or modify
@@ -158,6 +158,10 @@ const char *ofono_dbus_access_intf_name(enum ofono_dbus_access_intf intf);
const char *ofono_dbus_access_method_name(enum ofono_dbus_access_intf intf,
int method);
/* Since mer/1.24+git2 */
ofono_bool_t ofono_dbus_access_method_allowed(const char *sender,
enum ofono_dbus_access_intf iface, int method, const char *arg);
#ifdef __cplusplus
}
#endif

View File

@@ -0,0 +1,55 @@
/*
* oFono - Open Source Telephony
*
* Copyright (C) 2021 Jolla Ltd.
* Copyright (C) 2021 Open Mobile Platform LLC.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*/
#ifndef OFONO_DBUS_CLIENTS_H
#define OFONO_DBUS_CLIENTS_H
#include <ofono/types.h>
#include <ofono/dbus.h>
/* Since mer/1.23+git31 */
struct ofono_dbus_clients;
typedef void (*ofono_dbus_clients_notify_func)(const char *name,
void *user_data);
struct ofono_dbus_clients *ofono_dbus_clients_new(DBusConnection *conn,
ofono_dbus_clients_notify_func notify, void *user_data);
void ofono_dbus_clients_free(struct ofono_dbus_clients *clients);
unsigned int ofono_dbus_clients_count(struct ofono_dbus_clients *clients);
ofono_bool_t ofono_dbus_clients_add(struct ofono_dbus_clients *clients,
const char *name);
ofono_bool_t ofono_dbus_clients_remove(struct ofono_dbus_clients *clients,
const char *name);
void ofono_dbus_clients_signal(struct ofono_dbus_clients *clients,
DBusMessage *signal);
void ofono_dbus_clients_signal_property_changed(struct ofono_dbus_clients *dc,
const char *path, const char *interface, const char *name,
int type, const void *value);
#endif /* OFONO_DBUS_CLIENTS_H */
/*
* Local Variables:
* mode: C
* c-basic-offset: 8
* indent-tabs-mode: t
* End:
*/

View File

@@ -3,7 +3,7 @@
* oFono - Open Telephony stack for Linux
*
* Copyright (C) 2008-2011 Intel Corporation. All rights reserved.
* Copyright (C) 2013-2016 Jolla Ltd.
* Copyright (C) 2013-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -14,10 +14,6 @@
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*
*/
#ifndef __OFONO_DBUS_H
@@ -83,6 +79,8 @@ extern "C" {
DBUS_TYPE_VARIANT_AS_STRING \
DBUS_DICT_ENTRY_END_CHAR_AS_STRING
#define OFONO_ERROR_INTERFACE "org.ofono.Error"
DBusConnection *ofono_dbus_get_connection(void);
void ofono_dbus_dict_append(DBusMessageIter *dict, const char *key, int type,
@@ -110,6 +108,36 @@ int ofono_dbus_signal_dict_property_changed(DBusConnection *conn,
const char *name, int type,
const void *value);
/* Since mer/1.23+git31 */
DBusMessage *ofono_dbus_signal_new_property_changed(const char *path,
const char *interface,
const char *name,
int type, const void *value);
/* Since mer/1.24+git2 */
DBusMessage *ofono_dbus_error_invalid_args(DBusMessage *msg);
DBusMessage *ofono_dbus_error_invalid_format(DBusMessage *msg);
DBusMessage *ofono_dbus_error_not_implemented(DBusMessage *msg);
DBusMessage *ofono_dbus_error_failed(DBusMessage *msg);
DBusMessage *ofono_dbus_error_busy(DBusMessage *msg);
DBusMessage *ofono_dbus_error_not_found(DBusMessage *msg);
DBusMessage *ofono_dbus_error_not_active(DBusMessage *msg);
DBusMessage *ofono_dbus_error_not_supported(DBusMessage *msg);
DBusMessage *ofono_dbus_error_not_available(DBusMessage *msg);
DBusMessage *ofono_dbus_error_timed_out(DBusMessage *msg);
DBusMessage *ofono_dbus_error_sim_not_ready(DBusMessage *msg);
DBusMessage *ofono_dbus_error_in_use(DBusMessage *msg);
DBusMessage *ofono_dbus_error_not_attached(DBusMessage *msg);
DBusMessage *ofono_dbus_error_attach_in_progress(DBusMessage *msg);
DBusMessage *ofono_dbus_error_not_registered(DBusMessage *msg);
DBusMessage *ofono_dbus_error_canceled(DBusMessage *msg);
DBusMessage *ofono_dbus_error_access_denied(DBusMessage *msg);
DBusMessage *ofono_dbus_error_emergency_active(DBusMessage *msg);
DBusMessage *ofono_dbus_error_incorrect_password(DBusMessage *msg);
DBusMessage *ofono_dbus_error_not_allowed(DBusMessage *msg);
DBusMessage *ofono_dbus_error_not_recognized(DBusMessage *msg);
DBusMessage *ofono_dbus_error_network_terminated(DBusMessage *msg);
#ifdef __cplusplus
}
#endif

View File

@@ -3,6 +3,7 @@
* oFono - Open Source Telephony
*
* Copyright (C) 2008-2011 Intel Corporation. All rights reserved.
* Copyright (C) 2015-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -128,6 +129,8 @@ void ofono_gprs_context_set_ipv4_gateway(struct ofono_gprs_context *gc,
const char *gateway);
void ofono_gprs_context_set_ipv4_dns_servers(struct ofono_gprs_context *gc,
const char **dns);
void ofono_gprs_context_set_ipv4_proxy_cscf(struct ofono_gprs_context *gc,
const char **pcscf); /* Since mer/1.23+git30 */
void ofono_gprs_context_set_ipv6_address(struct ofono_gprs_context *gc,
const char *address);
@@ -137,10 +140,15 @@ void ofono_gprs_context_set_ipv6_gateway(struct ofono_gprs_context *gc,
const char *gateway);
void ofono_gprs_context_set_ipv6_dns_servers(struct ofono_gprs_context *gc,
const char **dns);
void ofono_gprs_context_set_ipv6_proxy_cscf(struct ofono_gprs_context *gc,
const char **pcscf); /* Since mer/1.23+git30 */
void ofono_gprs_context_signal_change(struct ofono_gprs_context *gc,
unsigned int cid);
enum ofono_gprs_context_type ofono_gprs_context_get_assigned_type(
struct ofono_gprs_context *gc); /* Since mer/1.24+git2 */
#ifdef __cplusplus
}
#endif

View File

@@ -3,6 +3,7 @@
* oFono - Open Telephony stack for Linux
*
* Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
* Copyright (C) 2015-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -55,6 +56,14 @@ int ofono_gprs_provision_driver_register(
void ofono_gprs_provision_driver_unregister(
const struct ofono_gprs_provision_driver *driver);
/* Since mer/1.24+git2 */
ofono_bool_t ofono_gprs_provision_get_settings(const char *mcc,
const char *mnc, const char *spn,
struct ofono_gprs_provision_data **settings,
int *count);
void ofono_gprs_provision_free_settings(
struct ofono_gprs_provision_data *settings,
int count);
#ifdef __cplusplus
}
#endif

View File

@@ -3,6 +3,7 @@
* oFono - Open Source Telephony
*
* Copyright (C) 2008-2011 Intel Corporation. All rights reserved.
* Copyright (C) 2017-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -87,6 +88,9 @@ void ofono_gprs_attached_update(struct ofono_gprs *gprs);
const struct ofono_gprs_primary_context *ofono_gprs_context_settings_by_type
(struct ofono_gprs *gprs, enum ofono_gprs_context_type type);
/* Since mer/1.24+git2 */
ofono_bool_t ofono_gprs_get_roaming_allowed(struct ofono_gprs *gprs);
#ifdef __cplusplus
}
#endif

View File

@@ -38,7 +38,7 @@ typedef void (*ofono_lte_cb_t)(const struct ofono_error *error, void *data);
struct ofono_lte_driver {
const char *name;
int (*probe)(struct ofono_lte *lte, void *data);
int (*probe)(struct ofono_lte *lte, unsigned int vendor, void *data);
void (*remove)(struct ofono_lte *lte);
void (*set_default_attach_info)(const struct ofono_lte *lte,
const struct ofono_lte_default_attach_info *info,
@@ -50,6 +50,7 @@ int ofono_lte_driver_register(const struct ofono_lte_driver *d);
void ofono_lte_driver_unregister(const struct ofono_lte_driver *d);
struct ofono_lte *ofono_lte_create(struct ofono_modem *modem,
unsigned int vendor,
const char *driver, void *data);
void ofono_lte_register(struct ofono_lte *lte);

67
ofono/include/misc.h Normal file
View File

@@ -0,0 +1,67 @@
/*
* oFono - Open Source Telephony
*
* Copyright (C) 2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*/
#ifndef __OFONO_MISC_H
#define __OFONO_MISC_H
/*
* Miscellaneous utilities which do not fall into any other category.
*
* This file exists since mer/1.24+git2
*/
#ifdef __cplusplus
extern "C" {
#endif
#include <ofono/netreg.h>
const char *ofono_netreg_status_to_string(enum ofono_netreg_status status);
const char *ofono_access_technology_to_string(enum ofono_access_technology t);
char *ofono_sim_string_to_utf8(const unsigned char *buffer, int length);
void ofono_sim_string_free(char *str);
void ofono_encode_hex(const void *in, unsigned int n, char out[/* 2*n+1 */]);
#define OFONO_UNPACK_7BIT_USSD (0x01) /* flags */
unsigned int ofono_unpack_7bit(const void *in, unsigned int len,
unsigned int flags, void *out_buf, unsigned int out_buf_size);
#define OFONO_PHONE_NUMBER_BUFFER_SIZE (OFONO_MAX_PHONE_NUMBER_LENGTH + 2)
const char *ofono_phone_number_to_string(const struct ofono_phone_number *ph,
char buffer[/* OFONO_PHONE_NUMBER_BUFFER_SIZE */]);
#define OFONO_EF_PATH_BUFFER_SIZE 6
unsigned int ofono_get_ef_path_2g(unsigned short id,
unsigned char path[/* OFONO_EF_PATH_BUFFER_SIZE */]);
unsigned int ofono_get_ef_path_3g(unsigned short id,
unsigned char path[/* OFONO_EF_PATH_BUFFER_SIZE */]);
ofono_bool_t ofono_parse_get_response_2g(const void *response, unsigned int len,
unsigned int *file_len, unsigned int *record_len,
unsigned int *structure, unsigned char *access,
unsigned char *file_status);
ofono_bool_t ofono_parse_get_response_3g(const void *response, unsigned int len,
unsigned int *file_len, unsigned int *record_len,
unsigned int *structure, unsigned char *access,
unsigned short *efid);
ofono_bool_t ofono_decode_cbs_dcs_charset(unsigned char dcs,
enum ofono_sms_charset *charset);
#ifdef __cplusplus
}
#endif
#endif /* __OFONO_MISC_H */

View File

@@ -3,6 +3,7 @@
* oFono - Open Source Telephony
*
* Copyright (C) 2008-2011 Intel Corporation. All rights reserved.
* Copyright (C) 2015-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -86,6 +87,9 @@ const char *ofono_modem_get_path(struct ofono_modem *modem);
struct ofono_sim *ofono_modem_get_sim(struct ofono_modem *modem);
struct ofono_gprs *ofono_modem_get_gprs(struct ofono_modem *modem);
struct ofono_voicecall *ofono_modem_get_voicecall(struct ofono_modem *modem);
struct ofono_netreg *ofono_modem_get_netreg(struct ofono_modem *modem);
struct ofono_radio_settings *ofono_modem_get_radio_settings
(struct ofono_modem *modem); /* Since mer/1.24+git2 */
void ofono_modem_set_data(struct ofono_modem *modem, void *data);
void *ofono_modem_get_data(struct ofono_modem *modem);

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony
*
* Copyright (C) 2016-2017 Jolla Ltd.
* Copyright (C) 2016-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -13,13 +13,15 @@
* GNU General Public License for more details.
*/
#ifndef MTU_WATCH_H
#define MTU_WATCH_H
#ifndef __OFONO_MTU_LIMIT_H
#define __OFONO_MTU_LIMIT_H
struct mtu_watch;
/* This API exists since mer/1.24+git2 */
struct mtu_watch *mtu_watch_new(int max_mtu);
void mtu_watch_free(struct mtu_watch *mw);
void mtu_watch_set_ifname(struct mtu_watch *mw, const char *ifname);
struct ofono_mtu_limit;
#endif /* MTU_WATCH_H */
struct ofono_mtu_limit *ofono_mtu_limit_new(int max_mtu);
void ofono_mtu_limit_free(struct ofono_mtu_limit *ml);
void ofono_mtu_limit_set_ifname(struct ofono_mtu_limit *ml, const char *ifname);
#endif /* __OFONO_MTU_LIMIT_H */

View File

@@ -3,6 +3,7 @@
* oFono - Open Source Telephony
*
* Copyright (C) 2008-2011 Intel Corporation. All rights reserved.
* Copyright (C) 2015-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -28,8 +29,28 @@ extern "C" {
#include <ofono/types.h>
struct ofono_modem;
struct ofono_netreg;
enum ofono_netreg_status {
OFONO_NETREG_STATUS_NONE = -1,
/* 27.007 Section 7.2 <stat> */
OFONO_NETREG_STATUS_NOT_REGISTERED = 0,
OFONO_NETREG_STATUS_REGISTERED = 1,
OFONO_NETREG_STATUS_SEARCHING = 2,
OFONO_NETREG_STATUS_DENIED = 3,
OFONO_NETREG_STATUS_UNKNOWN = 4,
OFONO_NETREG_STATUS_ROAMING = 5
}; /* Since mer/1.24+git2 */
/* 27.007 Section 7.3 <stat> */
enum ofono_operator_status {
OFONO_OPERATOR_STATUS_UNKNOWN = 0,
OFONO_OPERATOR_STATUS_AVAILABLE = 1,
OFONO_OPERATOR_STATUS_CURRENT = 2,
OFONO_OPERATOR_STATUS_FORBIDDEN = 3
}; /* Since mer/1.24+git2 */
/* Theoretical limit is 16, but each GSM char can be encoded into
* * 3 UTF8 characters resulting in 16*3=48 chars
* */
@@ -39,8 +60,8 @@ struct ofono_network_operator {
char name[OFONO_MAX_OPERATOR_NAME_LENGTH + 1];
char mcc[OFONO_MAX_MCC_LENGTH + 1];
char mnc[OFONO_MAX_MNC_LENGTH + 1];
int status;
int tech;
enum ofono_operator_status status;
enum ofono_access_technology tech;
};
typedef void (*ofono_netreg_operator_cb_t)(const struct ofono_error *error,
@@ -110,13 +131,17 @@ void *ofono_netreg_get_data(struct ofono_netreg *netreg);
int ofono_netreg_get_location(struct ofono_netreg *netreg);
int ofono_netreg_get_cellid(struct ofono_netreg *netreg);
int ofono_netreg_get_status(struct ofono_netreg *netreg);
enum ofono_netreg_status ofono_netreg_get_status(struct ofono_netreg *netreg);
int ofono_netreg_get_technology(struct ofono_netreg *netreg);
const char *ofono_netreg_get_mcc(struct ofono_netreg *netreg);
const char *ofono_netreg_get_mnc(struct ofono_netreg *netreg);
const char *ofono_netreg_get_name(struct ofono_netreg *netreg);
struct sim_spdi *ofono_netreg_get_spdi(struct ofono_netreg *netreg);
/* Since mer/1.24+git2 */
ofono_bool_t ofono_netreg_spdi_lookup(struct ofono_netreg *netreg,
const char *mcc, const char *mnc);
#ifdef __cplusplus
}
#endif

View File

@@ -3,6 +3,7 @@
* oFono - Open Source Telephony
*
* Copyright (C) 2010 Nokia Corporation and/or its subsidiary(-ies).
* Copyright (C) 2015-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -139,6 +140,8 @@ struct ofono_modem *ofono_radio_settings_get_modem(
const char *ofono_radio_access_mode_to_string(enum ofono_radio_access_mode m);
ofono_bool_t ofono_radio_access_mode_from_string(const char *str,
enum ofono_radio_access_mode *mode);
enum ofono_radio_access_mode ofono_radio_access_max_mode( /* mer/1.24+git2 */
enum ofono_radio_access_mode mask);
#ifdef __cplusplus
}

View File

@@ -4,6 +4,7 @@
*
* Copyright (C) 2011 Nokia Corporation and/or its subsidiary(-ies).
* Copyright (C) 2013 Canonical Ltd.
* Copyright (C) 2015-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -27,17 +28,21 @@
extern "C" {
#endif
struct ofono_sim_mnclength_driver {
const char *name;
int (*get_mnclength)(const char *imsi);
/* Since mer/1.24+git2 */
int (*get_mnclength_mccmnc)(int mcc, int mnc);
};
int ofono_sim_mnclength_driver_register(
struct ofono_sim_mnclength_driver *driver);
const struct ofono_sim_mnclength_driver *driver);
void ofono_sim_mnclength_driver_unregister(
const struct ofono_sim_mnclength_driver *driver);
/* Since mer/1.24+git2 */
int ofono_sim_mnclength_get_mnclength(const char *imsi);
int ofono_sim_mnclength_get_mnclength_mccmnc(int mcc, int mnc);
#ifdef __cplusplus
}

View File

@@ -241,6 +241,10 @@ const unsigned char *ofono_sim_get_cphs_service_table(struct ofono_sim *sim);
enum ofono_sim_password_type ofono_sim_get_password_type(struct ofono_sim *sim);
void ofono_sim_refresh_full(struct ofono_sim *sim); /* Since mer/1.24+git2 */
enum ofono_sim_password_type ofono_sim_puk2pin( /* Since mer/1.24+git2 */
enum ofono_sim_password_type type);
unsigned int ofono_sim_add_state_watch(struct ofono_sim *sim,
ofono_sim_state_event_cb_t cb,
void *data, ofono_destroy_func destroy);

159
ofono/include/slot.h Normal file
View File

@@ -0,0 +1,159 @@
/*
* oFono - Open Source Telephony
*
* Copyright (C) 2017-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*/
#ifndef __OFONO_SLOT_H
#define __OFONO_SLOT_H
/*
* Slots are built-in non-removable modems. Which may or may not apprear
* in the list reported by org.ofono.Manager.GetModems D-Bus call.
*
* This API exists since mer/1.24+git2
*/
#ifdef __cplusplus
extern "C" {
#endif
struct ofono_modem;
#include <ofono/types.h>
#include <ofono/radio-settings.h>
enum ofono_slot_sim_presence {
OFONO_SLOT_SIM_UNKNOWN,
OFONO_SLOT_SIM_ABSENT,
OFONO_SLOT_SIM_PRESENT
};
/* Should be treated as a bitmask although currently it's not */
enum ofono_slot_data_role {
OFONO_SLOT_DATA_NONE = 0,
OFONO_SLOT_DATA_MMS = 0x01,
OFONO_SLOT_DATA_INTERNET = 0x02
};
enum ofono_slot_property {
OFONO_SLOT_PROPERTY_ANY,
OFONO_SLOT_PROPERTY_ENABLED,
OFONO_SLOT_PROPERTY_SIM_PRESENCE,
OFONO_SLOT_PROPERTY_DATA_ROLE
#define OFONO_SLOT_PROPERTY_LAST OFONO_SLOT_PROPERTY_DATA_ROLE
};
enum ofono_slot_manager_property {
OFONO_SLOT_MANAGER_PROPERTY_ANY,
OFONO_SLOT_MANAGER_PROPERTY_MMS_IMSI,
OFONO_SLOT_MANAGER_PROPERTY_MMS_PATH,
OFONO_SLOT_MANAGER_PROPERTY_DEFAULT_VOICE_IMSI,
OFONO_SLOT_MANAGER_PROPERTY_DEFAULT_DATA_IMSI,
OFONO_SLOT_MANAGER_PROPERTY_DEFAULT_VOICE_PATH,
OFONO_SLOT_MANAGER_PROPERTY_DEFAULT_DATA_PATH,
OFONO_SLOT_MANAGER_PROPERTY_READY
#define OFONO_SLOT_MANAGER_PROPERTY_LAST OFONO_SLOT_MANAGER_PROPERTY_READY
};
enum ofono_slot_flags {
OFONO_SLOT_NO_FLAGS = 0,
/* Normally we should be able to have two simultaneously active
* data contexts - one for mobile data and one for MMS. The flag
* below says that for whatever reason it's impossible and mobile
* data has to be disconnected before we can send or receive MMS.
* On such devices it may not be a good idea to automatically
* download MMS because that would kill active mobile data
* connections. */
OFONO_SLOT_FLAG_SINGLE_CONTEXT = 0x01
};
typedef struct ofono_slot {
const char *path;
const char *imei;
const char *imeisv;
ofono_bool_t enabled;
enum ofono_slot_sim_presence sim_presence;
enum ofono_slot_data_role data_role;
} const *ofono_slot_ptr;
struct ofono_slot_manager {
const char *mms_imsi;
const char *mms_path;
const char *default_voice_imsi;
const char *default_data_imsi;
const char *default_voice_path;
const char *default_data_path;
const ofono_slot_ptr *slots;
ofono_bool_t ready;
};
#define OFONO_SLOT_API_VERSION (1)
struct ofono_slot_driver {
const char *name;
int api_version; /* OFONO_SLOT_API_VERSION */
struct ofono_slot_driver_data *(*init)(struct ofono_slot_manager *m);
unsigned int (*start)(struct ofono_slot_driver_data *d);
void (*cancel)(struct ofono_slot_driver_data *d, unsigned int id);
void (*cleanup)(struct ofono_slot_driver_data *d);
};
typedef void (*ofono_slot_property_cb)(struct ofono_slot *slot,
enum ofono_slot_property property, void* user_data);
typedef void (*ofono_slot_manager_property_cb)(struct ofono_slot_manager *m,
enum ofono_slot_property property, void* user_data);
struct ofono_slot_driver_data;
struct ofono_slot_driver_reg;
struct ofono_slot_driver_reg *ofono_slot_driver_register
(const struct ofono_slot_driver *driver);
struct ofono_slot_driver_data *ofono_slot_driver_get_data
(struct ofono_slot_driver_reg *reg);
void ofono_slot_driver_unregister(struct ofono_slot_driver_reg *reg);
void ofono_slot_driver_started(struct ofono_slot_driver_reg *reg);
struct ofono_slot_manager *ofono_slot_manager_ref(struct ofono_slot_manager *m);
void ofono_slot_manager_unref(struct ofono_slot_manager *m);
void ofono_slot_manager_error(struct ofono_slot_manager *m, const char *key,
const char *message);
unsigned long ofono_slot_manager_add_property_handler
(struct ofono_slot_manager *m, enum ofono_slot_manager_property p,
ofono_slot_manager_property_cb cb, void* data);
void ofono_slot_manager_remove_handler(struct ofono_slot_manager *m,
unsigned long id);
void ofono_slot_manager_remove_handlers(struct ofono_slot_manager *m,
unsigned long *ids, unsigned int n);
struct ofono_cell_info;
struct ofono_slot *ofono_slot_add(struct ofono_slot_manager *m,
const char *path, enum ofono_radio_access_mode techs, const char *imei,
const char *imeisv, enum ofono_slot_sim_presence sim_presence,
enum ofono_slot_flags flags);
struct ofono_slot *ofono_slot_ref(struct ofono_slot *s);
void ofono_slot_unref(struct ofono_slot *s);
void ofono_slot_error(struct ofono_slot *s, const char *key, const char *msg);
void ofono_slot_set_cell_info(struct ofono_slot *s, struct ofono_cell_info *ci);
unsigned long ofono_slot_add_property_handler(struct ofono_slot *s,
enum ofono_slot_property p, ofono_slot_property_cb cb, void* data);
void ofono_slot_remove_handler(struct ofono_slot *s, unsigned long id);
void ofono_slot_remove_handlers(struct ofono_slot *s, unsigned long *ids,
unsigned int n);
void ofono_slot_set_sim_presence(struct ofono_slot *s,
enum ofono_slot_sim_presence sim_presence);
#ifdef __cplusplus
}
#endif
#endif /* __OFONO_SLOT_H */

View File

@@ -3,6 +3,7 @@
* oFono - Open Source Telephony
*
* Copyright (C) 2008-2011 Intel Corporation. All rights reserved.
* Copyright (C) 2015-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -42,11 +43,61 @@ typedef int ofono_bool_t;
typedef void (*ofono_destroy_func)(void *data);
enum ofono_access_technology {
OFONO_ACCESS_TECHNOLOGY_NONE = -1,
/* 27.007 Section 7.3 <AcT> */
OFONO_ACCESS_TECHNOLOGY_GSM = 0,
OFONO_ACCESS_TECHNOLOGY_GSM_COMPACT = 1,
OFONO_ACCESS_TECHNOLOGY_UTRAN = 2,
OFONO_ACCESS_TECHNOLOGY_GSM_EGPRS = 3,
OFONO_ACCESS_TECHNOLOGY_UTRAN_HSDPA = 4,
OFONO_ACCESS_TECHNOLOGY_UTRAN_HSUPA = 5,
OFONO_ACCESS_TECHNOLOGY_UTRAN_HSDPA_HSUPA = 6,
OFONO_ACCESS_TECHNOLOGY_EUTRAN = 7
};
/* 27.007 Section 6.2 */
enum ofono_clir_option {
OFONO_CLIR_OPTION_DEFAULT = 0,
OFONO_CLIR_OPTION_INVOCATION,
OFONO_CLIR_OPTION_SUPPRESSION,
OFONO_CLIR_OPTION_INVOCATION = 1,
OFONO_CLIR_OPTION_SUPPRESSION = 2,
};
/* 27.007 Section 7.6 */
enum ofono_clip_validity {
OFONO_CLIP_VALIDITY_VALID = 0,
OFONO_CLIP_VALIDITY_WITHHELD = 1,
OFONO_CLIP_VALIDITY_NOT_AVAILABLE = 2
};
/* 27.007 Section 7.30 */
enum ofono_cnap_validity {
OFONO_CNAP_VALIDITY_VALID = 0,
OFONO_CNAP_VALIDITY_WITHHELD = 1,
OFONO_CNAP_VALIDITY_NOT_AVAILABLE = 2
};
/* 27.007 Section 7.18 */
enum ofono_call_status {
OFONO_CALL_STATUS_ACTIVE = 0,
OFONO_CALL_STATUS_HELD = 1,
OFONO_CALL_STATUS_DIALING = 2,
OFONO_CALL_STATUS_ALERTING = 3,
OFONO_CALL_STATUS_INCOMING = 4,
OFONO_CALL_STATUS_WAITING = 5,
OFONO_CALL_STATUS_DISCONNECTED
};
/* 27.007 Section 7.18 */
enum ofono_call_direction {
OFONO_CALL_DIRECTION_MOBILE_ORIGINATED = 0,
OFONO_CALL_DIRECTION_MOBILE_TERMINATED = 1
};
enum ofono_sms_charset {
OFONO_SMS_CHARSET_7BIT = 0,
OFONO_SMS_CHARSET_8BIT = 1,
OFONO_SMS_CHARSET_UCS2 = 2
};
enum ofono_error_type {
@@ -96,13 +147,13 @@ struct ofono_cdma_phone_number {
struct ofono_call {
unsigned int id;
int type;
int direction;
int status;
enum ofono_call_direction direction;
enum ofono_call_status status;
struct ofono_phone_number phone_number;
struct ofono_phone_number called_number;
char name[OFONO_MAX_CALLER_NAME_LENGTH + 1];
int clip_validity;
int cnap_validity;
enum ofono_clip_validity clip_validity;
enum ofono_cnap_validity cnap_validity;
};
struct ofono_network_time {

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony
*
* Copyright (C) 2018 Jolla Ltd.
* Copyright (C) 2018-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -22,37 +22,6 @@ extern "C" {
#include <ofono/voicecall.h>
/* 27.007 Section 7.6 */
enum ofono_clip_validity {
OFONO_CLIP_VALIDITY_VALID = 0,
OFONO_CLIP_VALIDITY_WITHHELD,
OFONO_CLIP_VALIDITY_NOT_AVAILABLE
};
/* 27.007 Section 7.18 */
enum ofono_call_status {
OFONO_CALL_STATUS_ACTIVE = 0,
OFONO_CALL_STATUS_HELD,
OFONO_CALL_STATUS_DIALING,
OFONO_CALL_STATUS_ALERTING,
OFONO_CALL_STATUS_INCOMING,
OFONO_CALL_STATUS_WAITING,
OFONO_CALL_STATUS_DISCONNECTED
};
/* 27.007 Section 7.18 */
enum ofono_call_direction {
OFONO_CALL_DIRECTION_MOBILE_ORIGINATED = 0,
OFONO_CALL_DIRECTION_MOBILE_TERMINATED
};
/* 27.007 Section 7.30 */
enum ofono_cnap_validity {
OFONO_CNAP_VALIDITY_VALID = 0,
OFONO_CNAP_VALIDITY_WITHHELD,
OFONO_CNAP_VALIDITY_NOT_AVAILABLE
};
enum ofono_voicecall_filter_dial_result {
OFONO_VOICECALL_FILTER_DIAL_CONTINUE, /* Run the next filter */
OFONO_VOICECALL_FILTER_DIAL_BLOCK /* Don't dial*/

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony
*
* Copyright (C) 2017-2019 Jolla Ltd.
* Copyright (C) 2017-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -17,21 +17,12 @@
#define OFONO_WATCH_H
#include <ofono/gprs-context.h>
#include <ofono/netreg.h>
struct ofono_modem;
struct ofono_sim;
struct ofono_netreg;
enum ofono_netreg_status {
OFONO_NETREG_STATUS_NONE = -1,
OFONO_NETREG_STATUS_NOT_REGISTERED = 0,
OFONO_NETREG_STATUS_REGISTERED = 1,
OFONO_NETREG_STATUS_SEARCHING = 2,
OFONO_NETREG_STATUS_DENIED = 3,
OFONO_NETREG_STATUS_UNKNOWN = 4,
OFONO_NETREG_STATUS_ROAMING = 5
};
/* This object watches ofono modem and various other things */
struct ofono_watch {
const char *path;

View File

@@ -53,6 +53,11 @@
#define HARDWARE_MONITOR_INTERFACE OFONO_SERVICE ".cinterion.HardwareMonitor"
/* Supported gemalto's modem */
#define GEMALTO_MODEL_PHS8P "0053"
/* ALS3, PLS8-E, and PLS8-X family */
#define GEMALTO_MODEL_ALS3_PLS8x "0061"
static const char *none_prefix[] = { NULL };
static const char *sctm_prefix[] = { "^SCTM:", NULL };
static const char *sbv_prefix[] = { "^SBV:", NULL };
@@ -70,6 +75,8 @@ struct gemalto_data {
gboolean have_sim;
struct at_util_sim_state_query *sim_state_query;
struct gemalto_hardware_monitor *hm;
guint modem_ready_id;
guint trial_cmd_id;
};
static int gemalto_probe(struct ofono_modem *modem)
@@ -107,10 +114,26 @@ static GAtChat *open_device(const char *device)
GAtSyntax *syntax;
GIOChannel *channel;
GAtChat *chat;
GHashTable *options;
options = g_hash_table_new(g_str_hash, g_str_equal);
if (options == NULL)
return NULL;
g_hash_table_insert(options, "Baud", "115200");
g_hash_table_insert(options, "StopBits", "1");
g_hash_table_insert(options, "DataBits", "8");
g_hash_table_insert(options, "Parity", "none");
g_hash_table_insert(options, "XonXoff", "off");
g_hash_table_insert(options, "RtsCts", "on");
g_hash_table_insert(options, "Local", "on");
g_hash_table_insert(options, "Read", "on");
DBG("Opening device %s", device);
channel = g_at_tty_open(device, NULL);
channel = g_at_tty_open(device, options);
g_hash_table_destroy(options);
if (channel == NULL)
return NULL;
@@ -125,6 +148,72 @@ static GAtChat *open_device(const char *device)
return chat;
}
static void sim_ready_cb(gboolean present, gpointer user_data)
{
struct ofono_modem *modem = user_data;
struct gemalto_data *data = ofono_modem_get_data(modem);
struct ofono_sim *sim = data->sim;
at_util_sim_state_query_free(data->sim_state_query);
data->sim_state_query = NULL;
DBG("sim present: %d", present);
ofono_sim_inserted_notify(sim, present);
}
static void gemalto_ciev_notify(GAtResult *result, gpointer user_data)
{
struct ofono_modem *modem = user_data;
struct gemalto_data *data = ofono_modem_get_data(modem);
struct ofono_sim *sim = data->sim;
const char *sim_status = "simstatus";
const char *ind_str;
int status;
GAtResultIter iter;
g_at_result_iter_init(&iter, result);
/* Example: +CIEV: simstatus,<status> */
if (!g_at_result_iter_next(&iter, "+CIEV:"))
return;
if (!g_at_result_iter_next_unquoted_string(&iter, &ind_str))
return;
if (!g_str_equal(sim_status, ind_str))
return;
if (!g_at_result_iter_next_number(&iter, &status))
return;
DBG("sim status %d", status);
switch (status) {
/* SIM is removed from the holder */
case 0:
ofono_sim_inserted_notify(sim, FALSE);
break;
/* SIM is inserted inside the holder */
case 1:
/* The SIM won't be ready yet */
data->sim_state_query = at_util_sim_state_query_new(data->app,
1, 20, sim_ready_cb, modem,
NULL);
break;
/* USIM initialization completed. UE has finished reading USIM data. */
case 5:
ofono_sim_initialized_notify(sim);
break;
default:
break;
}
}
static void sim_state_cb(gboolean present, gpointer user_data)
{
struct ofono_modem *modem = user_data;
@@ -135,6 +224,13 @@ static void sim_state_cb(gboolean present, gpointer user_data)
data->have_sim = present;
ofono_modem_set_powered(modem, TRUE);
/* Register for specific sim status reports */
g_at_chat_register(data->app, "+CIEV:",
gemalto_ciev_notify, FALSE, modem, NULL);
g_at_chat_send(data->app, "AT^SIND=\"simstatus\",1", none_prefix,
NULL, NULL, NULL);
}
static void cfun_enable(gboolean ok, GAtResult *result, gpointer user_data)
@@ -300,6 +396,79 @@ static int gemalto_hardware_monitor_enable(struct ofono_modem *modem)
return 0;
}
static void gemalto_initialize(struct ofono_modem *modem)
{
struct gemalto_data *data = ofono_modem_get_data(modem);
const char *mdm;
DBG("");
mdm = ofono_modem_get_string(modem, "Modem");
if (mdm == NULL)
return;
/* Open devices */
data->mdm = open_device(mdm);
if (data->mdm == NULL) {
g_at_chat_unref(data->app);
data->app = NULL;
return;
}
if (getenv("OFONO_AT_DEBUG")) {
g_at_chat_set_debug(data->app, gemalto_debug, "App");
g_at_chat_set_debug(data->mdm, gemalto_debug, "Mdm");
}
g_at_chat_send(data->mdm, "ATE0", none_prefix, NULL, NULL, NULL);
g_at_chat_send(data->app, "ATE0 +CMEE=1", none_prefix,
NULL, NULL, NULL);
g_at_chat_send(data->mdm, "AT&C0", none_prefix, NULL, NULL, NULL);
g_at_chat_send(data->app, "AT&C0", none_prefix, NULL, NULL, NULL);
g_at_chat_send(data->app, "AT+CFUN=4", none_prefix,
cfun_enable, modem, NULL);
gemalto_hardware_monitor_enable(modem);
}
static void gemalto_modem_ready(GAtResult *result, gpointer user_data)
{
struct ofono_modem *modem = user_data;
struct gemalto_data *data = ofono_modem_get_data(modem);
const char *app = ofono_modem_get_string(modem, "Application");
DBG("");
/*
* As the modem wasn't ready to handle AT commands when we opened
* it, we have to close and reopen the device app.
*/
data->modem_ready_id = 0;
data->trial_cmd_id = 0;
g_at_chat_unref(data->app);
data->app = open_device(app);
if (data->app == NULL) {
ofono_modem_set_powered(modem, FALSE);
} else {
gemalto_initialize(modem);
}
}
static void gemalto_at_cb(gboolean ok, GAtResult *result, gpointer user_data)
{
struct ofono_modem *modem = user_data;
struct gemalto_data *data = ofono_modem_get_data(modem);
g_at_chat_unregister(data->app, data->modem_ready_id);
data->modem_ready_id = 0;
gemalto_initialize(modem);
}
static int gemalto_enable(struct ofono_modem *modem)
{
struct gemalto_data *data = ofono_modem_get_data(modem);
@@ -318,28 +487,11 @@ static int gemalto_enable(struct ofono_modem *modem)
if (data->app == NULL)
return -EINVAL;
data->mdm = open_device(mdm);
if (data->mdm == NULL) {
g_at_chat_unref(data->app);
data->app = NULL;
return -EINVAL;
}
if (getenv("OFONO_AT_DEBUG")) {
g_at_chat_set_debug(data->app, gemalto_debug, "App");
g_at_chat_set_debug(data->mdm, gemalto_debug, "Mdm");
}
g_at_chat_send(data->mdm, "ATE0", none_prefix, NULL, NULL, NULL);
g_at_chat_send(data->app, "ATE0 +CMEE=1", none_prefix,
NULL, NULL, NULL);
g_at_chat_send(data->mdm, "AT&C0", none_prefix, NULL, NULL, NULL);
g_at_chat_send(data->app, "AT&C0", none_prefix, NULL, NULL, NULL);
g_at_chat_send(data->app, "AT+CFUN=4", none_prefix,
cfun_enable, modem, NULL);
gemalto_hardware_monitor_enable(modem);
/* Try the AT command. If it doesn't work, wait for ^SYSSTART */
data->modem_ready_id = g_at_chat_register(data->app, "^SYSSTART",
gemalto_modem_ready, FALSE, modem, NULL);
data->trial_cmd_id = g_at_chat_send(data->app, "ATE0 AT",
none_prefix, gemalto_at_cb, modem, NULL);
return -EINPROGRESS;
}
@@ -414,17 +566,16 @@ static void gemalto_set_online(struct ofono_modem *modem, ofono_bool_t online,
static void gemalto_pre_sim(struct ofono_modem *modem)
{
struct gemalto_data *data = ofono_modem_get_data(modem);
struct ofono_sim *sim;
DBG("%p", modem);
ofono_devinfo_create(modem, 0, "atmodem", data->app);
ofono_location_reporting_create(modem, 0, "gemaltomodem", data->app);
sim = ofono_sim_create(modem, OFONO_VENDOR_CINTERION, "atmodem",
data->sim = ofono_sim_create(modem, OFONO_VENDOR_CINTERION, "atmodem",
data->app);
if (sim && data->have_sim == TRUE)
ofono_sim_inserted_notify(sim, TRUE);
if (data->sim && data->have_sim == TRUE)
ofono_sim_inserted_notify(data->sim, TRUE);
}
static void gemalto_post_sim(struct ofono_modem *modem)
@@ -432,6 +583,7 @@ static void gemalto_post_sim(struct ofono_modem *modem)
struct gemalto_data *data = ofono_modem_get_data(modem);
struct ofono_gprs *gprs;
struct ofono_gprs_context *gc;
const char *model = ofono_modem_get_string(modem, "Model");
DBG("%p", modem);
@@ -444,6 +596,10 @@ static void gemalto_post_sim(struct ofono_modem *modem)
if (gprs && gc)
ofono_gprs_add_context(gprs, gc);
if (!g_strcmp0(model, GEMALTO_MODEL_ALS3_PLS8x))
ofono_lte_create(modem, OFONO_VENDOR_CINTERION,
"atmodem", data->app);
}
static void gemalto_post_online(struct ofono_modem *modem)

View File

@@ -264,56 +264,38 @@ static void create_shared_dms(void *user_data)
create_dms_cb, modem, NULL);
}
static void discover_cb(uint8_t count, const struct qmi_version *list,
void *user_data)
static void discover_cb(void *user_data)
{
struct ofono_modem *modem = user_data;
struct gobi_data *data = ofono_modem_get_data(modem);
uint8_t i;
uint16_t major, minor;
DBG("");
for (i = 0; i < count; i++) {
DBG("%s %d.%d - %d", list[i].name, list[i].major, list[i].minor,
list[i].type);
switch (list[i].type) {
case QMI_SERVICE_DMS:
data->features |= GOBI_DMS;
break;
case QMI_SERVICE_NAS:
data->features |= GOBI_NAS;
break;
case QMI_SERVICE_WMS:
data->features |= GOBI_WMS;
break;
case QMI_SERVICE_WDS:
data->features |= GOBI_WDS;
break;
case QMI_SERVICE_WDA:
data->features |= GOBI_WDA;
break;
case QMI_SERVICE_PDS:
data->features |= GOBI_PDS;
break;
case QMI_SERVICE_PBM:
data->features |= GOBI_PBM;
break;
case QMI_SERVICE_UIM:
data->features |= GOBI_UIM;
break;
case QMI_SERVICE_CAT:
data->features |= GOBI_CAT;
break;
case QMI_SERVICE_CAT_OLD:
if (list[i].major > 0)
data->features |= GOBI_CAT_OLD;
break;
case QMI_SERVICE_VOICE:
if (qmi_device_has_service(data->device, QMI_SERVICE_DMS))
data->features |= GOBI_DMS;
if (qmi_device_has_service(data->device, QMI_SERVICE_NAS))
data->features |= GOBI_NAS;
if (qmi_device_has_service(data->device, QMI_SERVICE_WMS))
data->features |= GOBI_WMS;
if (qmi_device_has_service(data->device, QMI_SERVICE_WDS))
data->features |= GOBI_WDS;
if (qmi_device_has_service(data->device, QMI_SERVICE_WDA))
data->features |= GOBI_WDA;
if (qmi_device_has_service(data->device, QMI_SERVICE_PDS))
data->features |= GOBI_PDS;
if (qmi_device_has_service(data->device, QMI_SERVICE_PBM))
data->features |= GOBI_PBM;
if (qmi_device_has_service(data->device, QMI_SERVICE_UIM))
data->features |= GOBI_UIM;
if (qmi_device_has_service(data->device, QMI_SERVICE_CAT))
data->features |= GOBI_CAT;
if (qmi_device_get_service_version(data->device,
QMI_SERVICE_CAT_OLD, &major, &minor))
if (major > 0)
data->features |= GOBI_CAT_OLD;
if (qmi_device_has_service(data->device, QMI_SERVICE_VOICE))
data->features |= GOBI_VOICE;
break;
}
}
if (!(data->features & GOBI_DMS)) {
if (++data->discover_attempts < 3) {
@@ -484,7 +466,7 @@ static void gobi_post_sim(struct ofono_modem *modem)
DBG("%p", modem);
ofono_lte_create(modem, "qmimodem", data->device);
ofono_lte_create(modem, 0, "qmimodem", data->device);
if (data->features & GOBI_CAT)
ofono_stk_create(modem, 0, "qmimodem", data->device);

View File

@@ -422,6 +422,8 @@ static struct ofono_modem_driver mbim_driver = {
static int mbim_init(void)
{
l_debug("------------------->Foobar");
return ofono_modem_driver_register(&mbim_driver);
}

View File

@@ -3,6 +3,7 @@
* oFono - Open Source Telephony
*
* Copyright (C) 2013 Canonical Ltd.
* Copyright (C) 2015-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -318,7 +319,7 @@ static int comp_mcc(const void *key, const void *value)
return mcc - mccmnc->mcc;
}
int mnclength(int mcc, int mnc)
static int mnclength_mccmnc(int mcc, int mnc)
{
int mccmnc_num = 1000*mcc + mnc;
int *mccmnc3_res = bsearch(&mccmnc_num, codes_mnclen3_db,
@@ -381,7 +382,8 @@ static int mnclength_get_mnclength(const char *imsi)
static struct ofono_sim_mnclength_driver mnclength_driver = {
.name = "MNC length",
.get_mnclength = mnclength_get_mnclength
.get_mnclength = mnclength_get_mnclength,
.get_mnclength_mccmnc = mnclength_mccmnc
};
static int mnclength_init(void)

View File

@@ -458,7 +458,7 @@ static void ril_post_sim(struct ofono_modem *modem)
}
if (ofono_modem_get_boolean(modem, MODEM_PROP_LTE_CAPABLE))
ofono_lte_create(modem, "rilmodem", rd->ril);
ofono_lte_create(modem, 0, "rilmodem", rd->ril);
ofono_stk_create(modem, 0, "rilmodem", rd->ril);
}

View File

@@ -1,598 +0,0 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2016-2018 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*/
#include "sailfish_cell_info_dbus.h"
#include "sailfish_cell_info.h"
#include <ofono/modem.h>
#include <ofono/dbus.h>
#include <ofono/log.h>
#include <gdbus.h>
struct sailfish_cell_entry {
guint cell_id;
char *path;
struct sailfish_cell cell;
};
struct sailfish_cell_info_dbus {
struct sailfish_cell_info *info;
DBusConnection *conn;
char *path;
gulong handler_id;
guint next_cell_id;
GSList *entries;
};
#define CELL_INFO_DBUS_INTERFACE "org.nemomobile.ofono.CellInfo"
#define CELL_INFO_DBUS_CELLS_ADDED_SIGNAL "CellsAdded"
#define CELL_INFO_DBUS_CELLS_REMOVED_SIGNAL "CellsRemoved"
#define CELL_DBUS_INTERFACE_VERSION (1)
#define CELL_DBUS_INTERFACE "org.nemomobile.ofono.Cell"
#define CELL_DBUS_REGISTERED_CHANGED_SIGNAL "RegisteredChanged"
#define CELL_DBUS_PROPERTY_CHANGED_SIGNAL "PropertyChanged"
#define CELL_DBUS_REMOVED_SIGNAL "Removed"
struct sailfish_cell_property {
const char *name;
glong off;
int flag;
};
#define CELL_GSM_PROPERTY(value,name) \
{ #name, G_STRUCT_OFFSET(struct sailfish_cell_info_gsm,name), value }
#define CELL_WCDMA_PROPERTY(value,name) \
{ #name, G_STRUCT_OFFSET(struct sailfish_cell_info_wcdma,name), value }
#define CELL_LTE_PROPERTY(value,name) \
{ #name, G_STRUCT_OFFSET(struct sailfish_cell_info_lte,name), value }
static const struct sailfish_cell_property sailfish_cell_gsm_properties [] = {
CELL_GSM_PROPERTY(0x001,mcc),
CELL_GSM_PROPERTY(0x002,mnc),
CELL_GSM_PROPERTY(0x004,lac),
CELL_GSM_PROPERTY(0x008,cid),
CELL_GSM_PROPERTY(0x010,arfcn),
CELL_GSM_PROPERTY(0x020,bsic),
CELL_GSM_PROPERTY(0x040,signalStrength),
CELL_GSM_PROPERTY(0x080,bitErrorRate),
CELL_GSM_PROPERTY(0x100,timingAdvance)
};
static const struct sailfish_cell_property sailfish_cell_wcdma_properties [] = {
CELL_WCDMA_PROPERTY(0x01,mcc),
CELL_WCDMA_PROPERTY(0x02,mnc),
CELL_WCDMA_PROPERTY(0x04,lac),
CELL_WCDMA_PROPERTY(0x08,cid),
CELL_WCDMA_PROPERTY(0x10,psc),
CELL_WCDMA_PROPERTY(0x20,uarfcn),
CELL_WCDMA_PROPERTY(0x40,signalStrength),
CELL_WCDMA_PROPERTY(0x80,bitErrorRate)
};
static const struct sailfish_cell_property sailfish_cell_lte_properties [] = {
CELL_LTE_PROPERTY(0x001,mcc),
CELL_LTE_PROPERTY(0x002,mnc),
CELL_LTE_PROPERTY(0x004,ci),
CELL_LTE_PROPERTY(0x008,pci),
CELL_LTE_PROPERTY(0x010,tac),
CELL_LTE_PROPERTY(0x020,earfcn),
CELL_LTE_PROPERTY(0x040,signalStrength),
CELL_LTE_PROPERTY(0x080,rsrp),
CELL_LTE_PROPERTY(0x100,rsrq),
CELL_LTE_PROPERTY(0x200,rssnr),
CELL_LTE_PROPERTY(0x400,cqi),
CELL_LTE_PROPERTY(0x800,timingAdvance)
};
#define SAILFISH_CELL_PROPERTY_REGISTERED 0x1000
typedef void (*sailfish_cell_info_dbus_append_fn)(DBusMessageIter *it,
const struct sailfish_cell_entry *entry);
static const char *sailfish_cell_info_dbus_cell_type_str
(enum sailfish_cell_type type)
{
switch (type) {
case SAILFISH_CELL_TYPE_GSM:
return "gsm";
case SAILFISH_CELL_TYPE_WCDMA:
return "wcdma";
case SAILFISH_CELL_TYPE_LTE:
return "lte";
default:
return "unknown";
}
};
static const struct sailfish_cell_property *
sailfish_cell_info_dbus_cell_properties(
enum sailfish_cell_type type, int *count)
{
switch (type) {
case SAILFISH_CELL_TYPE_GSM:
*count = G_N_ELEMENTS(sailfish_cell_gsm_properties);
return sailfish_cell_gsm_properties;
case SAILFISH_CELL_TYPE_WCDMA:
*count = G_N_ELEMENTS(sailfish_cell_wcdma_properties);
return sailfish_cell_wcdma_properties;
case SAILFISH_CELL_TYPE_LTE:
*count = G_N_ELEMENTS(sailfish_cell_lte_properties);
return sailfish_cell_lte_properties;
default:
*count = 0;
return NULL;
}
};
static void sailfish_cell_info_destroy_entry(struct sailfish_cell_entry *entry)
{
if (entry) {
g_free(entry->path);
g_free(entry);
}
}
static DBusMessage *sailfish_cell_info_dbus_reply(DBusMessage *msg,
const struct sailfish_cell_entry *entry,
sailfish_cell_info_dbus_append_fn append)
{
DBusMessage *reply = dbus_message_new_method_return(msg);
DBusMessageIter it;
dbus_message_iter_init_append(reply, &it);
append(&it, entry);
return reply;
}
static void sailfish_cell_info_dbus_append_version(DBusMessageIter *it,
const struct sailfish_cell_entry *entry)
{
dbus_int32_t version = CELL_DBUS_INTERFACE_VERSION;
dbus_message_iter_append_basic(it, DBUS_TYPE_INT32, &version);
}
static void sailfish_cell_info_dbus_append_type(DBusMessageIter *it,
const struct sailfish_cell_entry *entry)
{
const char *type =
sailfish_cell_info_dbus_cell_type_str(entry->cell.type);
dbus_message_iter_append_basic(it, DBUS_TYPE_STRING, &type);
}
static void sailfish_cell_info_dbus_append_registered(DBusMessageIter *it,
const struct sailfish_cell_entry *entry)
{
const dbus_bool_t registered = (entry->cell.registered != FALSE);
dbus_message_iter_append_basic(it, DBUS_TYPE_BOOLEAN, &registered);
}
static void sailfish_cell_info_dbus_append_properties(DBusMessageIter *it,
const struct sailfish_cell_entry *entry)
{
int i, n;
DBusMessageIter dict;
const struct sailfish_cell *cell = &entry->cell;
const struct sailfish_cell_property *prop =
sailfish_cell_info_dbus_cell_properties(cell->type, &n);
dbus_message_iter_open_container(it, DBUS_TYPE_ARRAY, "{sv}", &dict);
for (i = 0; i < n; i++) {
gint32 value = G_STRUCT_MEMBER(int, &cell->info, prop[i].off);
if (value != SAILFISH_CELL_INVALID_VALUE) {
ofono_dbus_dict_append(&dict, prop[i].name,
DBUS_TYPE_INT32, &value);
}
}
dbus_message_iter_close_container(it, &dict);
}
static void sailfish_cell_info_dbus_append_all(DBusMessageIter *it,
const struct sailfish_cell_entry *entry)
{
sailfish_cell_info_dbus_append_version(it, entry);
sailfish_cell_info_dbus_append_type(it, entry);
sailfish_cell_info_dbus_append_registered(it, entry);
sailfish_cell_info_dbus_append_properties(it, entry);
}
static DBusMessage *sailfish_cell_info_dbus_cell_get_all
(DBusConnection *conn, DBusMessage *msg, void *data)
{
return sailfish_cell_info_dbus_reply(msg, (struct sailfish_cell_entry*)
data, sailfish_cell_info_dbus_append_all);
}
static DBusMessage *sailfish_cell_info_dbus_cell_get_version
(DBusConnection *conn, DBusMessage *msg, void *data)
{
return sailfish_cell_info_dbus_reply(msg, (struct sailfish_cell_entry*)
data, sailfish_cell_info_dbus_append_version);
}
static DBusMessage *sailfish_cell_info_dbus_cell_get_type
(DBusConnection *conn, DBusMessage *msg, void *data)
{
return sailfish_cell_info_dbus_reply(msg, (struct sailfish_cell_entry*)
data, sailfish_cell_info_dbus_append_type);
}
static DBusMessage *sailfish_cell_info_dbus_cell_get_registered
(DBusConnection *conn, DBusMessage *msg, void *data)
{
return sailfish_cell_info_dbus_reply(msg, (struct sailfish_cell_entry*)
data, sailfish_cell_info_dbus_append_registered);
}
static DBusMessage *sailfish_cell_info_dbus_cell_get_properties
(DBusConnection *conn, DBusMessage *msg, void *data)
{
return sailfish_cell_info_dbus_reply(msg, (struct sailfish_cell_entry*)
data, sailfish_cell_info_dbus_append_properties);
}
static const GDBusMethodTable sailfish_cell_info_dbus_cell_methods[] = {
{ GDBUS_METHOD("GetAll", NULL,
GDBUS_ARGS({ "version", "i" },
{ "type", "s" },
{ "registered", "b" },
{ "properties", "a{sv}" }),
sailfish_cell_info_dbus_cell_get_all) },
{ GDBUS_METHOD("GetInterfaceVersion", NULL,
GDBUS_ARGS({ "version", "i" }),
sailfish_cell_info_dbus_cell_get_version) },
{ GDBUS_METHOD("GetType", NULL,
GDBUS_ARGS({ "type", "s" }),
sailfish_cell_info_dbus_cell_get_type) },
{ GDBUS_METHOD("GetRegistered", NULL,
GDBUS_ARGS({ "registered", "b" }),
sailfish_cell_info_dbus_cell_get_registered) },
{ GDBUS_METHOD("GetProperties", NULL,
GDBUS_ARGS({ "properties", "a{sv}" }),
sailfish_cell_info_dbus_cell_get_properties) },
{ }
};
static const GDBusSignalTable sailfish_cell_info_dbus_cell_signals[] = {
{ GDBUS_SIGNAL(CELL_DBUS_REGISTERED_CHANGED_SIGNAL,
GDBUS_ARGS({ "registered", "b" })) },
{ GDBUS_SIGNAL(CELL_DBUS_PROPERTY_CHANGED_SIGNAL,
GDBUS_ARGS({ "name", "s" }, { "value", "v" })) },
{ GDBUS_SIGNAL(CELL_DBUS_REMOVED_SIGNAL,
GDBUS_ARGS({})) },
{ }
};
static struct sailfish_cell_entry *sailfish_cell_info_dbus_find_id
(struct sailfish_cell_info_dbus *dbus, guint id)
{
GSList *l;
for (l = dbus->entries; l; l = l->next) {
struct sailfish_cell_entry *entry = l->data;
if (entry->cell_id == id) {
return entry;
}
}
return NULL;
}
static guint sailfish_cell_info_dbus_next_cell_id
(struct sailfish_cell_info_dbus *dbus)
{
while (sailfish_cell_info_dbus_find_id(dbus, dbus->next_cell_id)) {
dbus->next_cell_id++;
}
return dbus->next_cell_id++;
}
static struct sailfish_cell_entry *sailfish_cell_info_dbus_find_cell
(struct sailfish_cell_info_dbus *dbus,
const struct sailfish_cell *cell)
{
if (cell) {
GSList *l;
for (l = dbus->entries; l; l = l->next) {
struct sailfish_cell_entry *entry = l->data;
if (!sailfish_cell_compare_location(&entry->cell,
cell)) {
return entry;
}
}
}
return NULL;
}
static void sailfish_cell_info_dbus_emit_path_list
(struct sailfish_cell_info_dbus *dbus, const char *name,
GPtrArray *list)
{
guint i;
DBusMessageIter it, array;
DBusMessage *signal = dbus_message_new_signal(dbus->path,
CELL_INFO_DBUS_INTERFACE, name);
dbus_message_iter_init_append(signal, &it);
dbus_message_iter_open_container(&it, DBUS_TYPE_ARRAY, "o", &array);
for (i = 0; i < list->len; i++) {
const char* path = list->pdata[i];
dbus_message_iter_append_basic(&array, DBUS_TYPE_OBJECT_PATH,
&path);
}
dbus_message_iter_close_container(&it, &array);
g_dbus_send_message(dbus->conn, signal);
}
static int sailfish_cell_info_dbus_compare(const struct sailfish_cell *c1,
const struct sailfish_cell *c2)
{
if (c1->type == c2->type) {
int i, n, mask = 0;
const struct sailfish_cell_property *prop =
sailfish_cell_info_dbus_cell_properties(c1->type, &n);
if (c1->registered != c2->registered) {
mask |= SAILFISH_CELL_PROPERTY_REGISTERED;
}
for (i = 0; i < n; i++) {
const glong offset = prop[i].off;
gint32 v1 = G_STRUCT_MEMBER(int, &c1->info, offset);
gint32 v2 = G_STRUCT_MEMBER(int, &c2->info, offset);
if (v1 != v2) {
mask |= prop[i].flag;
}
}
return mask;
} else {
return -1;
}
}
static void sailfish_cell_info_dbus_property_changed
(struct sailfish_cell_info_dbus *dbus,
const struct sailfish_cell_entry *entry, int mask)
{
int i, n;
const struct sailfish_cell *cell = &entry->cell;
const struct sailfish_cell_property *prop =
sailfish_cell_info_dbus_cell_properties(cell->type, &n);
if (mask & SAILFISH_CELL_PROPERTY_REGISTERED) {
const dbus_bool_t registered = (cell->registered != FALSE);
g_dbus_emit_signal(dbus->conn, entry->path,
CELL_DBUS_INTERFACE,
CELL_DBUS_REGISTERED_CHANGED_SIGNAL,
DBUS_TYPE_BOOLEAN, &registered, DBUS_TYPE_INVALID);
mask &= ~SAILFISH_CELL_PROPERTY_REGISTERED;
}
for (i = 0; i < n && mask; i++) {
if (mask & prop[i].flag) {
ofono_dbus_signal_property_changed(dbus->conn,
entry->path, CELL_DBUS_INTERFACE,
prop[i].name, DBUS_TYPE_INT32,
G_STRUCT_MEMBER_P(&cell->info, prop[i].off));
mask &= ~prop[i].flag;
}
}
}
static void sailfish_cell_info_dbus_update_entries
(struct sailfish_cell_info_dbus *dbus, gboolean emit_signals)
{
GSList *l;
GPtrArray* added = NULL;
GPtrArray* removed = NULL;
/* Remove non-existent cells */
l = dbus->entries;
while (l) {
GSList *next = l->next;
struct sailfish_cell_entry *entry = l->data;
if (!g_slist_find_custom(dbus->info->cells, &entry->cell,
sailfish_cell_compare_func)) {
DBG("%s removed", entry->path);
dbus->entries = g_slist_delete_link(dbus->entries, l);
g_dbus_emit_signal(dbus->conn, entry->path,
CELL_DBUS_INTERFACE,
CELL_DBUS_REMOVED_SIGNAL,
DBUS_TYPE_INVALID);
g_dbus_unregister_interface(dbus->conn, entry->path,
CELL_DBUS_INTERFACE);
if (emit_signals) {
if (!removed) {
removed =
g_ptr_array_new_with_free_func(
g_free);
}
/* Steal the path */
g_ptr_array_add(removed, entry->path);
entry->path = NULL;
}
sailfish_cell_info_destroy_entry(entry);
}
l = next;
}
/* Add new cells */
for (l = dbus->info->cells; l; l = l->next) {
const struct sailfish_cell *cell = l->data;
struct sailfish_cell_entry *entry =
sailfish_cell_info_dbus_find_cell(dbus, cell);
if (entry) {
if (emit_signals) {
int diff = sailfish_cell_info_dbus_compare(cell,
&entry->cell);
entry->cell = *cell;
sailfish_cell_info_dbus_property_changed(dbus,
entry, diff);
} else {
entry->cell = *cell;
}
} else {
entry = g_new0(struct sailfish_cell_entry, 1);
entry->cell = *cell;
entry->cell_id =
sailfish_cell_info_dbus_next_cell_id(dbus);
entry->path = g_strdup_printf("%s/cell_%u", dbus->path,
entry->cell_id);
dbus->entries = g_slist_append(dbus->entries, entry);
DBG("%s added", entry->path);
g_dbus_register_interface(dbus->conn, entry->path,
CELL_DBUS_INTERFACE,
sailfish_cell_info_dbus_cell_methods,
sailfish_cell_info_dbus_cell_signals, NULL,
entry, NULL);
if (emit_signals) {
if (!added) {
added = g_ptr_array_new();
}
g_ptr_array_add(added, entry->path);
}
}
}
if (removed) {
sailfish_cell_info_dbus_emit_path_list(dbus,
CELL_INFO_DBUS_CELLS_REMOVED_SIGNAL, removed);
g_ptr_array_free(removed, TRUE);
}
if (added) {
sailfish_cell_info_dbus_emit_path_list(dbus,
CELL_INFO_DBUS_CELLS_ADDED_SIGNAL, added);
g_ptr_array_free(added, TRUE);
}
}
static void sailfish_cell_info_dbus_cells_changed_cb
(struct sailfish_cell_info *info, void *arg)
{
DBG("");
sailfish_cell_info_dbus_update_entries
((struct sailfish_cell_info_dbus *)arg, TRUE);
}
static DBusMessage *sailfish_cell_info_dbus_get_cells(DBusConnection *conn,
DBusMessage *msg, void *data)
{
struct sailfish_cell_info_dbus *dbus = data;
DBusMessage *reply = dbus_message_new_method_return(msg);
DBusMessageIter it, array;
GSList *l;
dbus_message_iter_init_append(reply, &it);
dbus_message_iter_open_container(&it, DBUS_TYPE_ARRAY, "o", &array);
for (l = dbus->entries; l; l = l->next) {
const struct sailfish_cell_entry *entry = l->data;
dbus_message_iter_append_basic(&array, DBUS_TYPE_OBJECT_PATH,
&entry->path);
}
dbus_message_iter_close_container(&it, &array);
return reply;
}
static const GDBusMethodTable sailfish_cell_info_dbus_methods[] = {
{ GDBUS_METHOD("GetCells", NULL,
GDBUS_ARGS({ "paths", "ao" }),
sailfish_cell_info_dbus_get_cells) },
{ }
};
static const GDBusSignalTable sailfish_cell_info_dbus_signals[] = {
{ GDBUS_SIGNAL(CELL_INFO_DBUS_CELLS_ADDED_SIGNAL,
GDBUS_ARGS({ "paths", "ao" })) },
{ GDBUS_SIGNAL(CELL_INFO_DBUS_CELLS_REMOVED_SIGNAL,
GDBUS_ARGS({ "paths", "ao" })) },
{ }
};
struct sailfish_cell_info_dbus *sailfish_cell_info_dbus_new
(struct ofono_modem *modem, struct sailfish_cell_info *info)
{
if (modem && info) {
struct sailfish_cell_info_dbus *dbus =
g_new0(struct sailfish_cell_info_dbus, 1);
DBG("%s", ofono_modem_get_path(modem));
dbus->path = g_strdup(ofono_modem_get_path(modem));
dbus->conn = dbus_connection_ref(ofono_dbus_get_connection());
dbus->info = sailfish_cell_info_ref(info);
dbus->handler_id =
sailfish_cell_info_add_cells_changed_handler(info,
sailfish_cell_info_dbus_cells_changed_cb, dbus);
/* Register D-Bus interface */
if (g_dbus_register_interface(dbus->conn, dbus->path,
CELL_INFO_DBUS_INTERFACE,
sailfish_cell_info_dbus_methods,
sailfish_cell_info_dbus_signals,
NULL, dbus, NULL)) {
ofono_modem_add_interface(modem,
CELL_INFO_DBUS_INTERFACE);
sailfish_cell_info_dbus_update_entries(dbus, FALSE);
return dbus;
} else {
ofono_error("CellInfo D-Bus register failed");
sailfish_cell_info_dbus_free(dbus);
}
}
return NULL;
}
void sailfish_cell_info_dbus_free(struct sailfish_cell_info_dbus *dbus)
{
if (dbus) {
GSList *l;
DBG("%s", dbus->path);
g_dbus_unregister_interface(dbus->conn, dbus->path,
CELL_INFO_DBUS_INTERFACE);
/* Unregister cells */
l = dbus->entries;
while (l) {
struct sailfish_cell_entry *entry = l->data;
g_dbus_unregister_interface(dbus->conn, entry->path,
CELL_DBUS_INTERFACE);
sailfish_cell_info_destroy_entry(entry);
l = l->next;
}
g_slist_free(dbus->entries);
dbus_connection_unref(dbus->conn);
sailfish_cell_info_remove_handler(dbus->info, dbus->handler_id);
sailfish_cell_info_unref(dbus->info);
g_free(dbus->path);
g_free(dbus);
}
}
/*
* Local Variables:
* mode: C
* c-basic-offset: 8
* indent-tabs-mode: t
* End:
*/

File diff suppressed because it is too large Load Diff

View File

@@ -1,143 +0,0 @@
/*
* oFono - Open Source Telephony
*
* Copyright (C) 2017 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*/
#ifndef SAILFISH_MANAGER_H
#define SAILFISH_MANAGER_H
struct ofono_modem;
#include <ofono/types.h>
#include <ofono/radio-settings.h>
#include <glib.h>
struct sailfish_manager;
struct sailfish_slot;
struct sailfish_slot_impl;
struct sailfish_slot_driver;
struct sailfish_slot_driver_reg;
struct sailfish_slot_manager;
struct sailfish_slot_manager_impl;
struct sailfish_cell_info;
typedef void (*sailfish_slot_manager_impl_cb_t)
(struct sailfish_slot_manager_impl *impl, void *user_data);
enum sailfish_slot_flags {
SAILFISH_SLOT_NO_FLAGS = 0,
/* Normally we should be able to have two simultaneously active
* data contexts - one for mobile data and one for MMS. The flag
* below says that for whatever reason it's impossible and mobile
* data has to be disconnected before we can send or receive MMS.
* On such devices it may not be a good idea to automatically
* download MMS because that would kill active mobile data
* connections. */
SAILFISH_SLOT_SINGLE_CONTEXT = 0x01
};
typedef struct sailfish_slot {
const char *path;
const char *imei;
const char *imeisv;
gboolean sim_present;
gboolean enabled;
} const *sailfish_slot_ptr;
struct sailfish_manager {
const char *mms_imsi;
const char *mms_path;
const char *default_voice_imsi;
const char *default_data_imsi;
const char *default_voice_path;
const char *default_data_path;
const sailfish_slot_ptr *slots;
gboolean ready;
};
enum sailfish_sim_state {
SAILFISH_SIM_STATE_UNKNOWN,
SAILFISH_SIM_STATE_ABSENT,
SAILFISH_SIM_STATE_PRESENT,
SAILFISH_SIM_STATE_ERROR
};
enum sailfish_data_role {
SAILFISH_DATA_ROLE_NONE, /* Data not allowed */
SAILFISH_DATA_ROLE_MMS, /* Data is allowed at any speed */
SAILFISH_DATA_ROLE_INTERNET /* Data is allowed at full speed */
};
/* Register/unregister the driver */
struct sailfish_slot_driver_reg *sailfish_slot_driver_register
(const struct sailfish_slot_driver *d);
void sailfish_slot_driver_unregister(struct sailfish_slot_driver_reg *r);
/* For use by the driver implementations */
void sailfish_manager_foreach_slot_manager
(struct sailfish_slot_driver_reg *r,
sailfish_slot_manager_impl_cb_t cb, void *user_data);
struct sailfish_slot *sailfish_manager_slot_add
(struct sailfish_slot_manager *m, struct sailfish_slot_impl *i,
const char *path, enum ofono_radio_access_mode techs,
const char *imei, const char *imeisv,
enum sailfish_sim_state sim_state);
struct sailfish_slot *sailfish_manager_slot_add2
(struct sailfish_slot_manager *m, struct sailfish_slot_impl *i,
const char *path, enum ofono_radio_access_mode techs,
const char *imei, const char *imeisv,
enum sailfish_sim_state sim_state,
enum sailfish_slot_flags flags);
void sailfish_manager_imei_obtained(struct sailfish_slot *s, const char *imei);
void sailfish_manager_imeisv_obtained(struct sailfish_slot *s,
const char *imeisv);
void sailfish_manager_set_sim_state(struct sailfish_slot *s,
enum sailfish_sim_state state);
void sailfish_slot_manager_started(struct sailfish_slot_manager *m);
void sailfish_manager_slot_error(struct sailfish_slot *s, const char *key,
const char *message);
void sailfish_manager_error(struct sailfish_slot_manager *m, const char *key,
const char *message);
void sailfish_manager_set_cell_info(struct sailfish_slot *s,
struct sailfish_cell_info *ci);
/* Callbacks provided by slot plugins */
struct sailfish_slot_driver {
const char *name;
int priority;
/* Slot manager methods */
struct sailfish_slot_manager_impl *(*manager_create)
(struct sailfish_slot_manager *m);
guint (*manager_start)(struct sailfish_slot_manager_impl *s);
void (*manager_cancel_start)(struct sailfish_slot_manager_impl *s,
guint id);
void (*manager_free)(struct sailfish_slot_manager_impl *s);
/* Slot methods */
void (*slot_enabled_changed)(struct sailfish_slot_impl *s);
void (*slot_set_data_role)(struct sailfish_slot_impl *s,
enum sailfish_data_role role);
void (*slot_free)(struct sailfish_slot_impl *s);
};
#endif /* SAILFISH_MANAGER_H */
/*
* Local Variables:
* mode: C
* c-basic-offset: 8
* indent-tabs-mode: t
* End:
*/

File diff suppressed because it is too large Load Diff

View File

@@ -1,77 +0,0 @@
/*
* oFono - Open Source Telephony
*
* Copyright (C) 2016-2017 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*/
#ifndef SAILFISH_MANAGER_DBUS_H
#define SAILFISH_MANAGER_DBUS_H
#include <sailfish_manager.h>
struct sailfish_manager_dbus;
enum sailfish_manager_dbus_block {
SAILFISH_MANAGER_DBUS_BLOCK_NONE = 0,
SAILFISH_MANAGER_DBUS_BLOCK_MODEM = 0x01,
SAILFISH_MANAGER_DBUS_BLOCK_IMEI = 0x02,
SAILFISH_MANAGER_DBUS_BLOCK_ALL = 0x03
};
enum sailfish_manager_dbus_signal {
SAILFISH_MANAGER_SIGNAL_NONE = 0,
SAILFISH_MANAGER_SIGNAL_VOICE_IMSI = 0x01,
SAILFISH_MANAGER_SIGNAL_DATA_IMSI = 0x02,
SAILFISH_MANAGER_SIGNAL_VOICE_PATH = 0x04,
SAILFISH_MANAGER_SIGNAL_DATA_PATH = 0x08,
SAILFISH_MANAGER_SIGNAL_ENABLED_SLOTS = 0x10,
SAILFISH_MANAGER_SIGNAL_MMS_IMSI = 0x20,
SAILFISH_MANAGER_SIGNAL_MMS_PATH = 0x40,
SAILFISH_MANAGER_SIGNAL_READY = 0x80
};
/* Functionality provided by sailfish_manager to sailfish_manager_dbus */
struct sailfish_manager_dbus_cb {
GHashTable *(*get_errors)(struct sailfish_manager *m);
GHashTable *(*get_slot_errors)(const struct sailfish_slot *s);
void (*set_enabled_slots)(struct sailfish_manager *m, char **slots);
gboolean (*set_mms_imsi)(struct sailfish_manager *m, const char *imsi);
void (*set_default_voice_imsi)(struct sailfish_manager *m,
const char *imsi);
void (*set_default_data_imsi)(struct sailfish_manager *m,
const char *imsi);
};
struct sailfish_manager_dbus *sailfish_manager_dbus_new
(struct sailfish_manager *m,
const struct sailfish_manager_dbus_cb *cb);
void sailfish_manager_dbus_free(struct sailfish_manager_dbus *d);
void sailfish_manager_dbus_set_block(struct sailfish_manager_dbus *d,
enum sailfish_manager_dbus_block b);
void sailfish_manager_dbus_signal(struct sailfish_manager_dbus *d,
enum sailfish_manager_dbus_signal m);
void sailfish_manager_dbus_signal_sim(struct sailfish_manager_dbus *d,
int index, gboolean present);
void sailfish_manager_dbus_signal_error(struct sailfish_manager_dbus *d,
const char *id, const char *message);
void sailfish_manager_dbus_signal_modem_error(struct sailfish_manager_dbus *d,
int index, const char *id, const char *msg);
#endif /* SAILFISH_MANAGER_DBUS_H */
/*
* Local Variables:
* mode: C
* c-basic-offset: 8
* indent-tabs-mode: t
* End:
*/

View File

@@ -1,80 +0,0 @@
/*
* oFono - Open Source Telephony
*
* Copyright (C) 2017-2018 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*/
#ifndef SAILFISH_SIM_INFO_H
#define SAILFISH_SIM_INFO_H
#include <ofono/types.h>
#include <glib.h>
#include <glib-object.h>
/*
* Note that iccid, imsi and spn provided by this class can be cached,
* i.e. become available before the pin code is entered and before those
* are known to the ofono core. That's the whole purpose of this thing.
*
* If you need to follow imsi known to the ofono core, you can use
* sailfish_sim_settings for that (or fight with ofono imsi watchers
* directly).
*/
struct ofono_modem;
struct sailfish_sim_info_priv;
struct sailfish_sim_info {
GObject object;
struct sailfish_sim_info_priv *priv;
const char *path;
const char *iccid;
const char *imsi;
const char *spn;
};
typedef void (*sailfish_sim_info_cb_t)(struct sailfish_sim_info *si,
void *user_data);
/* SIM info object associated with the particular slot */
struct sailfish_sim_info *sailfish_sim_info_new(const char *path);
struct sailfish_sim_info *sailfish_sim_info_ref(struct sailfish_sim_info *si);
void sailfish_sim_info_unref(struct sailfish_sim_info *si);
gulong sailfish_sim_info_add_iccid_changed_handler(struct sailfish_sim_info *si,
sailfish_sim_info_cb_t cb, void *user_data);
gulong sailfish_sim_info_add_imsi_changed_handler(struct sailfish_sim_info *si,
sailfish_sim_info_cb_t cb, void *user_data);
gulong sailfish_sim_info_add_spn_changed_handler(struct sailfish_sim_info *si,
sailfish_sim_info_cb_t cb, void *user_data);
void sailfish_sim_info_remove_handler(struct sailfish_sim_info *si, gulong id);
void sailfish_sim_info_remove_handlers(struct sailfish_sim_info *si,
gulong *ids, int count);
#define sailfish_sim_info_remove_all_handlers(si,ids) \
sailfish_sim_info_remove_handlers(si, ids, G_N_ELEMENTS(ids))
/* And the D-Bus interface for it */
struct sailfish_sim_info_dbus;
struct sailfish_sim_info_dbus *sailfish_sim_info_dbus_new
(struct sailfish_sim_info *si);
struct sailfish_sim_info_dbus *sailfish_sim_info_dbus_new_path
(const char *path);
void sailfish_sim_info_dbus_free(struct sailfish_sim_info_dbus *dbus);
#endif /* SAILFISH_SIM_INFO_H */
/*
* Local Variables:
* mode: C
* c-basic-offset: 8
* indent-tabs-mode: t
* End:
*/

273
ofono/plugins/sim7100.c Normal file
View File

@@ -0,0 +1,273 @@
/*
*
* oFono - Open Source Telephony
*
* Copyright (C) 2008-2011 Intel Corporation. All rights reserved.
* Copyright (C) 2009 Collabora Ltd. All rights reserved.
* Copyright 2018 Purism SPC
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
*
*/
/*
* This file was originally copied from g1.c and
* modified by Bob Ham <bob.ham@puri.sm>
*/
#ifdef HAVE_CONFIG_H
#include <config.h>
#endif
#include <stdlib.h>
#include <errno.h>
#include <glib.h>
#include <gatchat.h>
#include <gattty.h>
#define OFONO_API_SUBJECT_TO_CHANGE
#include <ofono/plugin.h>
#include <ofono/log.h>
#include <ofono/modem.h>
#include <ofono/call-barring.h>
#include <ofono/call-forwarding.h>
#include <ofono/call-meter.h>
#include <ofono/call-settings.h>
#include <ofono/devinfo.h>
#include <ofono/message-waiting.h>
#include <ofono/netreg.h>
#include <ofono/phonebook.h>
#include <ofono/sim.h>
#include <ofono/sms.h>
#include <ofono/ussd.h>
#include <ofono/voicecall.h>
#include <ofono/gprs.h>
#include <ofono/gprs-context.h>
#include <drivers/atmodem/vendor.h>
struct sim7100_data {
GAtChat *at;
GAtChat *ppp;
};
static void sim7100_debug(const char *str, void *user_data)
{
const char *prefix = user_data;
ofono_info("%s%s", prefix, str);
}
/* Detect hardware, and initialize if found */
static int sim7100_probe(struct ofono_modem *modem)
{
struct sim7100_data *data;
DBG("");
data = g_try_new0(struct sim7100_data, 1);
if (data == NULL)
return -ENOMEM;
ofono_modem_set_data(modem, data);
return 0;
}
static void sim7100_remove(struct ofono_modem *modem)
{
struct sim7100_data *data = ofono_modem_get_data(modem);
DBG("");
if (!data)
return;
if (data->at)
g_at_chat_unref(data->at);
if (data->ppp)
g_at_chat_unref(data->ppp);
ofono_modem_set_data(modem, NULL);
g_free (data);
}
static void cfun_set_on_cb(gboolean ok, GAtResult *result, gpointer user_data)
{
struct ofono_modem *modem = user_data;
DBG("");
if (ok)
ofono_modem_set_powered(modem, TRUE);
}
static int open_device(struct ofono_modem *modem, const char *devkey,
GAtChat **chatp)
{
GIOChannel *channel;
GAtSyntax *syntax;
GAtChat *chat;
const char *device;
DBG("devkey=%s", devkey);
device = ofono_modem_get_string(modem, devkey);
if (device == NULL)
return -EINVAL;
channel = g_at_tty_open(device, NULL);
if (channel == NULL)
return -EIO;
syntax = g_at_syntax_new_gsm_permissive();
chat = g_at_chat_new(channel, syntax);
g_at_syntax_unref(syntax);
g_io_channel_unref(channel);
if (chat == NULL)
return -EIO;
if (getenv("OFONO_AT_DEBUG"))
g_at_chat_set_debug(chat, sim7100_debug, "");
*chatp = chat;
return 0;
}
static int sim7100_enable(struct ofono_modem *modem)
{
struct sim7100_data *data = ofono_modem_get_data(modem);
int err;
DBG("");
err = open_device(modem, "AT", &data->at);
if (err < 0)
return err;
err = open_device(modem, "PPP", &data->ppp);
if (err < 0)
return err;
/* ensure modem is in a known state; verbose on, echo/quiet off */
g_at_chat_send(data->at, "ATE0Q0V1", NULL, NULL, NULL, NULL);
/* power up modem */
g_at_chat_send(data->at, "AT+CFUN=1", NULL, cfun_set_on_cb,
modem, NULL);
return 0;
}
static void cfun_set_off_cb(gboolean ok, GAtResult *result, gpointer user_data)
{
struct ofono_modem *modem = user_data;
struct sim7100_data *data = ofono_modem_get_data(modem);
DBG("");
g_at_chat_unref(data->ppp);
g_at_chat_unref(data->at);
data->at = data->ppp = NULL;
if (ok)
ofono_modem_set_powered(modem, FALSE);
}
static int sim7100_disable(struct ofono_modem *modem)
{
struct sim7100_data *data = ofono_modem_get_data(modem);
DBG("");
/* power down modem */
g_at_chat_cancel_all(data->ppp);
g_at_chat_cancel_all(data->at);
g_at_chat_unregister_all(data->ppp);
g_at_chat_unregister_all(data->at);
g_at_chat_send(data->at, "AT+CFUN=0", NULL, cfun_set_off_cb,
modem, NULL);
return -EINPROGRESS;
}
static void sim7100_pre_sim(struct ofono_modem *modem)
{
struct sim7100_data *data = ofono_modem_get_data(modem);
struct ofono_sim *sim;
DBG("");
ofono_devinfo_create(modem, 0, "atmodem", data->at);
sim = ofono_sim_create(modem, 0, "atmodem", data->at);
ofono_voicecall_create(modem, OFONO_VENDOR_SIMCOM, "atmodem", data->at);
if (sim)
ofono_sim_inserted_notify(sim, TRUE);
}
static void sim7100_post_sim(struct ofono_modem *modem)
{
struct sim7100_data *data = ofono_modem_get_data(modem);
struct ofono_message_waiting *mw;
struct ofono_gprs *gprs = NULL;
struct ofono_gprs_context *gc = NULL;
DBG("");
ofono_ussd_create(modem, 0, "atmodem", data->at);
ofono_call_forwarding_create(modem, 0, "atmodem", data->at);
ofono_call_settings_create(modem, 0, "atmodem", data->at);
ofono_netreg_create(modem, 0, "atmodem", data->at);
ofono_call_meter_create(modem, 0, "atmodem", data->at);
ofono_call_barring_create(modem, 0, "atmodem", data->at);
ofono_sms_create(modem, OFONO_VENDOR_SIMCOM, "atmodem", data->at);
ofono_phonebook_create(modem, 0, "atmodem", data->at);
gprs = ofono_gprs_create(modem, 0, "atmodem", data->at);
gc = ofono_gprs_context_create(modem, 0, "atmodem", data->ppp);
if (gprs && gc)
ofono_gprs_add_context(gprs, gc);
mw = ofono_message_waiting_create(modem);
if (mw)
ofono_message_waiting_register(mw);
}
static struct ofono_modem_driver sim7100_driver = {
.name = "sim7100",
.probe = sim7100_probe,
.remove = sim7100_remove,
.enable = sim7100_enable,
.disable = sim7100_disable,
.pre_sim = sim7100_pre_sim,
.post_sim = sim7100_post_sim,
};
static int sim7100_init(void)
{
return ofono_modem_driver_register(&sim7100_driver);
}
static void sim7100_exit(void)
{
ofono_modem_driver_unregister(&sim7100_driver);
}
OFONO_PLUGIN_DEFINE(sim7100, "SIMCom SIM7100E modem driver", VERSION,
OFONO_PLUGIN_PRIORITY_DEFAULT, sim7100_init, sim7100_exit)

View File

@@ -319,7 +319,7 @@ static void ublox_post_sim(struct ofono_modem *modem)
--ncontexts;
}
ofono_lte_create(modem, "ubloxmodem", data->aux);
ofono_lte_create(modem, 0, "ubloxmodem", data->aux);
}
static void ublox_post_online(struct ofono_modem *modem)

View File

@@ -710,7 +710,7 @@ static gboolean setup_telitqmi(struct modem_info *modem)
return TRUE;
}
static gboolean setup_simcom(struct modem_info *modem)
static gboolean setup_sim900(struct modem_info *modem)
{
const char *mdm = NULL, *aux = NULL, *gps = NULL, *diag = NULL;
GSList *list;
@@ -1132,6 +1132,7 @@ static gboolean setup_gemalto(struct modem_info* modem)
DBG("%s %s %s %s %s", info->devnode, info->interface,
info->number, info->label, info->subsystem);
/* PHS8-P */
if (g_strcmp0(info->interface, "255/255/255") == 0) {
if (g_strcmp0(info->number, "01") == 0)
gps = info->devnode;
@@ -1144,6 +1145,20 @@ static gboolean setup_gemalto(struct modem_info* modem)
else if (g_strcmp0(info->subsystem, "usbmisc") == 0)
qmi = info->devnode;
}
/* Cinterion ALS3, PLS8-E, PLS8-X */
if (g_strcmp0(info->interface, "2/2/1") == 0) {
if (g_strcmp0(info->number, "00") == 0)
mdm = info->devnode;
else if (g_strcmp0(info->number, "02") == 0)
app = info->devnode;
else if (g_strcmp0(info->number, "04") == 0)
gps = info->devnode;
}
if (g_strcmp0(info->interface, "2/6/0") == 0) {
if (g_strcmp0(info->subsystem, "net") == 0)
net = info->devnode;
}
}
DBG("application=%s gps=%s modem=%s network=%s qmi=%s",
@@ -1156,6 +1171,7 @@ static gboolean setup_gemalto(struct modem_info* modem)
ofono_modem_set_string(modem->modem, "GPS", gps);
ofono_modem_set_string(modem->modem, "Modem", mdm);
ofono_modem_set_string(modem->modem, "Device", qmi);
ofono_modem_set_string(modem->modem, "Model", modem->model);
ofono_modem_set_string(modem->modem, "NetworkInterface", net);
return TRUE;
@@ -1196,6 +1212,54 @@ static gboolean setup_xmm7xxx(struct modem_info *modem)
return TRUE;
}
static gboolean setup_sim7100(struct modem_info *modem)
{
const char *at = NULL, *ppp = NULL, *gps = NULL, *diag = NULL, *audio = NULL;
GSList *list;
DBG("%s", modem->syspath);
for (list = modem->devices; list; list = list->next) {
struct device_info *info = list->data;
DBG("%s %s", info->devnode, info->number);
/*
* Serial port layout:
* 0: QCDM/DIAG
* 1: NMEA
* 2: AT
* 3: AT/PPP
* 4: audio
*
* -- https://www.spinics.net/lists/linux-usb/msg135728.html
*/
if (g_strcmp0(info->number, "00") == 0)
diag = info->devnode;
else if (g_strcmp0(info->number, "01") == 0)
gps = info->devnode;
else if (g_strcmp0(info->number, "02") == 0)
at = info->devnode;
else if (g_strcmp0(info->number, "03") == 0)
ppp = info->devnode;
else if (g_strcmp0(info->number, "04") == 0)
audio = info->devnode;
}
if (at == NULL)
return FALSE;
DBG("at=%s ppp=%s gps=%s diag=%s, audio=%s", at, ppp, gps, diag, audio);
ofono_modem_set_string(modem->modem, "AT", at);
ofono_modem_set_string(modem->modem, "PPP", ppp);
ofono_modem_set_string(modem->modem, "GPS", gps);
ofono_modem_set_string(modem->modem, "Diag", diag);
ofono_modem_set_string(modem->modem, "Audio", audio);
return TRUE;
}
static struct {
const char *name;
gboolean (*setup)(struct modem_info *modem);
@@ -1215,7 +1279,8 @@ static struct {
{ "nokia", setup_nokia },
{ "telit", setup_telit, "device/interface" },
{ "telitqmi", setup_telitqmi },
{ "simcom", setup_simcom },
{ "sim900", setup_sim900 },
{ "sim7100", setup_sim7100 },
{ "zte", setup_zte },
{ "icera", setup_icera },
{ "samsung", setup_samsung },
@@ -1579,7 +1644,8 @@ static struct {
{ "alcatel", "option", "1bbb", "0017" },
{ "novatel", "option", "1410" },
{ "zte", "option", "19d2" },
{ "simcom", "option", "05c6", "9000" },
{ "sim900", "option", "05c6", "9000" },
{ "sim7100", "option", "1e0e", "9001" },
{ "telit", "usbserial", "1bc7" },
{ "telit", "option", "1bc7" },
{ "telit", "cdc_acm", "1bc7", "0021" },
@@ -1600,10 +1666,12 @@ static struct {
{ "gemalto", "option", "1e2d", "0053" },
{ "gemalto", "cdc_wdm", "1e2d", "0053" },
{ "gemalto", "qmi_wwan", "1e2d", "0053" },
{ "gemalto", "cdc_acm", "1e2d", "0061" },
{ "gemalto", "cdc_ether", "1e2d", "0061" },
{ "telit", "cdc_ncm", "1bc7", "0036" },
{ "telit", "cdc_acm", "1bc7", "0036" },
{ "xmm7xxx", "cdc_acm", "8087", "0930" },
{ "xmm7xxx", "cdc_ncm", "8087", "0930" },
{ "xmm7xxx", "cdc_acm", "8087" },
{ "xmm7xxx", "cdc_ncm", "8087" },
{ }
};
@@ -1733,7 +1801,11 @@ static gboolean create_modem(gpointer key, gpointer value, gpointer user_data)
if (driver_list[i].setup(modem) == TRUE) {
ofono_modem_set_string(modem->modem, "SystemPath",
syspath);
ofono_modem_register(modem->modem);
if (ofono_modem_register(modem->modem) < 0) {
DBG("could not register modem '%s'", modem->driver);
return TRUE;
}
return FALSE;
}
}

View File

@@ -323,7 +323,7 @@ static void xmm7xxx_post_sim(struct ofono_modem *modem)
{
struct xmm7xxx_data *data = ofono_modem_get_data(modem);
ofono_lte_create(modem, "atmodem", data->chat);
ofono_lte_create(modem, 0, "atmodem", data->chat);
ofono_radio_settings_create(modem, 0, "xmm7modem", data->chat);
ofono_sim_auth_create(modem);
}

View File

@@ -268,7 +268,7 @@ static void set_new_cond_list(struct ofono_call_forwarding *cf,
const char *number;
dbus_uint16_t timeout;
char attr[64];
char tattr[64];
char tattr[72];
gboolean update_sim = FALSE;
gboolean old_cfu;
gboolean new_cfu;

View File

@@ -115,6 +115,8 @@ static const GDBusMethodTable cdma_netreg_manager_methods[] = {
};
static const GDBusSignalTable cdma_netreg_manager_signals[] = {
{ GDBUS_SIGNAL("PropertyChanged",
GDBUS_ARGS({ "name", "s" }, { "value", "v" })) },
{ }
};

677
ofono/src/cell-info-dbus.c Normal file
View File

@@ -0,0 +1,677 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2016-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
* published by the Free Software Foundation.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*/
#include "cell-info-dbus.h"
#include <ofono/cell-info.h>
#include <ofono/modem.h>
#include <ofono/dbus.h>
#include <ofono/dbus-clients.h>
#include <ofono/log.h>
#include <gdbus.h>
#include "ofono.h"
typedef struct cell_entry {
guint cell_id;
char *path;
struct ofono_cell cell;
} CellEntry;
typedef struct cell_info_dbus {
struct ofono_cell_info *info;
DBusConnection *conn;
char *path;
gulong handler_id;
guint next_cell_id;
GSList *entries;
struct ofono_dbus_clients *clients;
} CellInfoDBus;
#define CELL_INFO_DBUS_INTERFACE "org.nemomobile.ofono.CellInfo"
#define CELL_INFO_DBUS_CELLS_ADDED_SIGNAL "CellsAdded"
#define CELL_INFO_DBUS_CELLS_REMOVED_SIGNAL "CellsRemoved"
#define CELL_INFO_DBUS_UNSUBSCRIBED_SIGNAL "Unsubscribed"
#define CELL_DBUS_INTERFACE_VERSION (1)
#define CELL_DBUS_INTERFACE "org.nemomobile.ofono.Cell"
#define CELL_DBUS_REGISTERED_CHANGED_SIGNAL "RegisteredChanged"
#define CELL_DBUS_PROPERTY_CHANGED_SIGNAL "PropertyChanged"
#define CELL_DBUS_REMOVED_SIGNAL "Removed"
struct cell_property {
const char *name;
glong off;
int flag;
};
#define CELL_GSM_PROPERTY(value,name) \
{ #name, G_STRUCT_OFFSET(struct ofono_cell_info_gsm,name), value }
#define CELL_WCDMA_PROPERTY(value,name) \
{ #name, G_STRUCT_OFFSET(struct ofono_cell_info_wcdma,name), value }
#define CELL_LTE_PROPERTY(value,name) \
{ #name, G_STRUCT_OFFSET(struct ofono_cell_info_lte,name), value }
static const struct cell_property cell_gsm_properties [] = {
CELL_GSM_PROPERTY(0x001,mcc),
CELL_GSM_PROPERTY(0x002,mnc),
CELL_GSM_PROPERTY(0x004,lac),
CELL_GSM_PROPERTY(0x008,cid),
CELL_GSM_PROPERTY(0x010,arfcn),
CELL_GSM_PROPERTY(0x020,bsic),
CELL_GSM_PROPERTY(0x040,signalStrength),
CELL_GSM_PROPERTY(0x080,bitErrorRate),
CELL_GSM_PROPERTY(0x100,timingAdvance)
};
static const struct cell_property cell_wcdma_properties [] = {
CELL_WCDMA_PROPERTY(0x01,mcc),
CELL_WCDMA_PROPERTY(0x02,mnc),
CELL_WCDMA_PROPERTY(0x04,lac),
CELL_WCDMA_PROPERTY(0x08,cid),
CELL_WCDMA_PROPERTY(0x10,psc),
CELL_WCDMA_PROPERTY(0x20,uarfcn),
CELL_WCDMA_PROPERTY(0x40,signalStrength),
CELL_WCDMA_PROPERTY(0x80,bitErrorRate)
};
static const struct cell_property cell_lte_properties [] = {
CELL_LTE_PROPERTY(0x001,mcc),
CELL_LTE_PROPERTY(0x002,mnc),
CELL_LTE_PROPERTY(0x004,ci),
CELL_LTE_PROPERTY(0x008,pci),
CELL_LTE_PROPERTY(0x010,tac),
CELL_LTE_PROPERTY(0x020,earfcn),
CELL_LTE_PROPERTY(0x040,signalStrength),
CELL_LTE_PROPERTY(0x080,rsrp),
CELL_LTE_PROPERTY(0x100,rsrq),
CELL_LTE_PROPERTY(0x200,rssnr),
CELL_LTE_PROPERTY(0x400,cqi),
CELL_LTE_PROPERTY(0x800,timingAdvance)
};
#define CELL_PROPERTY_REGISTERED 0x1000
typedef void (*cell_info_dbus_append_fn)(DBusMessageIter *it,
const CellEntry *entry);
static const char *cell_info_dbus_cell_type_str(enum ofono_cell_type type)
{
switch (type) {
case OFONO_CELL_TYPE_GSM:
return "gsm";
case OFONO_CELL_TYPE_WCDMA:
return "wcdma";
case OFONO_CELL_TYPE_LTE:
return "lte";
default:
return "unknown";
}
};
static const struct cell_property *cell_info_dbus_cell_properties
(enum ofono_cell_type type, int *count)
{
switch (type) {
case OFONO_CELL_TYPE_GSM:
*count = G_N_ELEMENTS(cell_gsm_properties);
return cell_gsm_properties;
case OFONO_CELL_TYPE_WCDMA:
*count = G_N_ELEMENTS(cell_wcdma_properties);
return cell_wcdma_properties;
case OFONO_CELL_TYPE_LTE:
*count = G_N_ELEMENTS(cell_lte_properties);
return cell_lte_properties;
default:
*count = 0;
return NULL;
}
};
static void cell_info_destroy_entry(CellEntry *entry)
{
if (entry) {
g_free(entry->path);
g_free(entry);
}
}
static DBusMessage *cell_info_dbus_reply(DBusMessage *msg,
const CellEntry *entry, cell_info_dbus_append_fn append)
{
DBusMessage *reply = dbus_message_new_method_return(msg);
DBusMessageIter it;
dbus_message_iter_init_append(reply, &it);
append(&it, entry);
return reply;
}
static void cell_info_dbus_append_version(DBusMessageIter *it,
const CellEntry *entry)
{
dbus_int32_t version = CELL_DBUS_INTERFACE_VERSION;
dbus_message_iter_append_basic(it, DBUS_TYPE_INT32, &version);
}
static void cell_info_dbus_append_type(DBusMessageIter *it,
const CellEntry *entry)
{
const char *type = cell_info_dbus_cell_type_str(entry->cell.type);
dbus_message_iter_append_basic(it, DBUS_TYPE_STRING, &type);
}
static void cell_info_dbus_append_registered(DBusMessageIter *it,
const CellEntry *entry)
{
const dbus_bool_t registered = (entry->cell.registered != FALSE);
dbus_message_iter_append_basic(it, DBUS_TYPE_BOOLEAN, &registered);
}
static void cell_info_dbus_append_properties(DBusMessageIter *it,
const CellEntry *entry)
{
int i, n;
DBusMessageIter dict;
const struct ofono_cell *cell = &entry->cell;
const struct cell_property *prop =
cell_info_dbus_cell_properties(cell->type, &n);
dbus_message_iter_open_container(it, DBUS_TYPE_ARRAY, "{sv}", &dict);
for (i = 0; i < n; i++) {
gint32 value = G_STRUCT_MEMBER(int, &cell->info, prop[i].off);
if (value != OFONO_CELL_INVALID_VALUE) {
ofono_dbus_dict_append(&dict, prop[i].name,
DBUS_TYPE_INT32, &value);
}
}
dbus_message_iter_close_container(it, &dict);
}
static void cell_info_dbus_append_all(DBusMessageIter *it, const CellEntry *ce)
{
cell_info_dbus_append_version(it, ce);
cell_info_dbus_append_type(it, ce);
cell_info_dbus_append_registered(it, ce);
cell_info_dbus_append_properties(it, ce);
}
static DBusMessage *cell_info_dbus_cell_get_all(DBusConnection *conn,
DBusMessage *msg, void *data)
{
return cell_info_dbus_reply(msg, (CellEntry*) data,
cell_info_dbus_append_all);
}
static DBusMessage *cell_info_dbus_cell_get_version(DBusConnection *conn,
DBusMessage *msg, void *data)
{
return cell_info_dbus_reply(msg, (CellEntry*) data,
cell_info_dbus_append_version);
}
static DBusMessage *cell_info_dbus_cell_get_type(DBusConnection *conn,
DBusMessage *msg, void *data)
{
return cell_info_dbus_reply(msg, (CellEntry*) data,
cell_info_dbus_append_type);
}
static DBusMessage *cell_info_dbus_cell_get_registered(DBusConnection *conn,
DBusMessage *msg, void *data)
{
return cell_info_dbus_reply(msg, (CellEntry*) data,
cell_info_dbus_append_registered);
}
static DBusMessage *cell_info_dbus_cell_get_properties(DBusConnection *conn,
DBusMessage *msg, void *data)
{
return cell_info_dbus_reply(msg, (CellEntry*) data,
cell_info_dbus_append_properties);
}
static const GDBusMethodTable cell_info_dbus_cell_methods[] = {
{ GDBUS_METHOD("GetAll", NULL,
GDBUS_ARGS({ "version", "i" },
{ "type", "s" },
{ "registered", "b" },
{ "properties", "a{sv}" }),
cell_info_dbus_cell_get_all) },
{ GDBUS_METHOD("GetInterfaceVersion", NULL,
GDBUS_ARGS({ "version", "i" }),
cell_info_dbus_cell_get_version) },
{ GDBUS_METHOD("GetType", NULL,
GDBUS_ARGS({ "type", "s" }),
cell_info_dbus_cell_get_type) },
{ GDBUS_METHOD("GetRegistered", NULL,
GDBUS_ARGS({ "registered", "b" }),
cell_info_dbus_cell_get_registered) },
{ GDBUS_METHOD("GetProperties", NULL,
GDBUS_ARGS({ "properties", "a{sv}" }),
cell_info_dbus_cell_get_properties) },
{ }
};
static const GDBusSignalTable cell_info_dbus_cell_signals[] = {
{ GDBUS_SIGNAL(CELL_DBUS_REGISTERED_CHANGED_SIGNAL,
GDBUS_ARGS({ "registered", "b" })) },
{ GDBUS_SIGNAL(CELL_DBUS_PROPERTY_CHANGED_SIGNAL,
GDBUS_ARGS({ "name", "s" }, { "value", "v" })) },
{ GDBUS_SIGNAL(CELL_DBUS_REMOVED_SIGNAL,
GDBUS_ARGS({})) },
{ }
};
static CellEntry *cell_info_dbus_find_id(CellInfoDBus *dbus, guint id)
{
GSList *l;
for (l = dbus->entries; l; l = l->next) {
CellEntry *entry = l->data;
if (entry->cell_id == id) {
return entry;
}
}
return NULL;
}
static guint cell_info_dbus_next_cell_id(CellInfoDBus *dbus)
{
while (cell_info_dbus_find_id(dbus, dbus->next_cell_id)) {
dbus->next_cell_id++;
}
return dbus->next_cell_id++;
}
static const struct ofono_cell *cell_info_dbus_find_ofono_cell
(struct ofono_cell_info *info, const struct ofono_cell *cell)
{
const ofono_cell_ptr *c;
for (c = info->cells; *c; c++) {
if (!ofono_cell_compare_location(*c, cell)) {
return *c;
}
}
return NULL;
}
static CellEntry *cell_info_dbus_find_cell(CellInfoDBus *dbus,
const struct ofono_cell *cell)
{
if (cell) {
GSList *l;
for (l = dbus->entries; l; l = l->next) {
CellEntry *e = l->data;
if (!ofono_cell_compare_location(&e->cell, cell)) {
return e;
}
}
}
return NULL;
}
static void cell_info_dbus_emit_path_list(CellInfoDBus *dbus, const char *name,
GPtrArray *list)
{
if (ofono_dbus_clients_count(dbus->clients)) {
guint i;
DBusMessageIter it, a;
DBusMessage *signal = dbus_message_new_signal(dbus->path,
CELL_INFO_DBUS_INTERFACE, name);
dbus_message_iter_init_append(signal, &it);
dbus_message_iter_open_container(&it, DBUS_TYPE_ARRAY, "o", &a);
for (i = 0; i < list->len; i++) {
const char* path = list->pdata[i];
dbus_message_iter_append_basic(&a,
DBUS_TYPE_OBJECT_PATH, &path);
}
dbus_message_iter_close_container(&it, &a);
ofono_dbus_clients_signal(dbus->clients, signal);
dbus_message_unref(signal);
}
}
static int cell_info_dbus_compare(const struct ofono_cell *c1,
const struct ofono_cell *c2)
{
if (c1->type == c2->type) {
int i, n, mask = 0;
const struct cell_property *prop =
cell_info_dbus_cell_properties(c1->type, &n);
if (c1->registered != c2->registered) {
mask |= CELL_PROPERTY_REGISTERED;
}
for (i = 0; i < n; i++) {
const glong offset = prop[i].off;
gint32 v1 = G_STRUCT_MEMBER(int, &c1->info, offset);
gint32 v2 = G_STRUCT_MEMBER(int, &c2->info, offset);
if (v1 != v2) {
mask |= prop[i].flag;
}
}
return mask;
} else {
return -1;
}
}
static void cell_info_dbus_emit_signal(CellInfoDBus *dbus, const char *path,
const char *intf, const char *name, int type, ...)
{
if (ofono_dbus_clients_count(dbus->clients)) {
va_list args;
DBusMessage *signal = dbus_message_new_signal(path, intf, name);
va_start(args, type);
dbus_message_append_args_valist(signal, type, args);
ofono_dbus_clients_signal(dbus->clients, signal);
dbus_message_unref(signal);
va_end(args);
}
}
static void cell_info_dbus_property_changed(CellInfoDBus *dbus,
const CellEntry *entry, int mask)
{
int i, n;
const struct ofono_cell *cell = &entry->cell;
const struct cell_property *prop =
cell_info_dbus_cell_properties(cell->type, &n);
if (mask & CELL_PROPERTY_REGISTERED) {
const dbus_bool_t registered = (cell->registered != FALSE);
cell_info_dbus_emit_signal(dbus, entry->path,
CELL_DBUS_INTERFACE,
CELL_DBUS_REGISTERED_CHANGED_SIGNAL,
DBUS_TYPE_BOOLEAN, &registered, DBUS_TYPE_INVALID);
mask &= ~CELL_PROPERTY_REGISTERED;
}
for (i = 0; i < n && mask; i++) {
if (mask & prop[i].flag) {
ofono_dbus_clients_signal_property_changed(
dbus->clients, entry->path,
CELL_DBUS_INTERFACE, prop[i].name,
DBUS_TYPE_INT32,
G_STRUCT_MEMBER_P(&cell->info, prop[i].off));
mask &= ~prop[i].flag;
}
}
}
static void cell_info_dbus_update_entries(CellInfoDBus *dbus, gboolean emit)
{
GSList *l;
GPtrArray* added = NULL;
GPtrArray* removed = NULL;
const ofono_cell_ptr *c;
/* Remove non-existent cells */
l = dbus->entries;
while (l) {
GSList *next = l->next;
CellEntry *entry = l->data;
if (!cell_info_dbus_find_ofono_cell(dbus->info, &entry->cell)) {
DBG("%s removed", entry->path);
dbus->entries = g_slist_delete_link(dbus->entries, l);
cell_info_dbus_emit_signal(dbus, entry->path,
CELL_DBUS_INTERFACE,
CELL_DBUS_REMOVED_SIGNAL,
DBUS_TYPE_INVALID);
g_dbus_unregister_interface(dbus->conn, entry->path,
CELL_DBUS_INTERFACE);
if (emit) {
if (!removed) {
removed = g_ptr_array_new_with_free_func
(g_free);
}
/* Steal the path */
g_ptr_array_add(removed, entry->path);
entry->path = NULL;
}
cell_info_destroy_entry(entry);
}
l = next;
}
/* Add new cells */
for (c = dbus->info->cells; *c; c++) {
const struct ofono_cell *cell = *c;
CellEntry *entry = cell_info_dbus_find_cell(dbus, cell);
if (entry) {
if (emit) {
const int diff = cell_info_dbus_compare(cell,
&entry->cell);
entry->cell = *cell;
cell_info_dbus_property_changed(dbus, entry,
diff);
} else {
entry->cell = *cell;
}
} else {
entry = g_new0(CellEntry, 1);
entry->cell = *cell;
entry->cell_id = cell_info_dbus_next_cell_id(dbus);
entry->path = g_strdup_printf("%s/cell_%u", dbus->path,
entry->cell_id);
dbus->entries = g_slist_append(dbus->entries, entry);
DBG("%s added", entry->path);
g_dbus_register_interface(dbus->conn, entry->path,
CELL_DBUS_INTERFACE,
cell_info_dbus_cell_methods,
cell_info_dbus_cell_signals, NULL,
entry, NULL);
if (emit) {
if (!added) {
added = g_ptr_array_new();
}
g_ptr_array_add(added, entry->path);
}
}
}
if (removed) {
cell_info_dbus_emit_path_list(dbus,
CELL_INFO_DBUS_CELLS_REMOVED_SIGNAL, removed);
g_ptr_array_free(removed, TRUE);
}
if (added) {
cell_info_dbus_emit_path_list(dbus,
CELL_INFO_DBUS_CELLS_ADDED_SIGNAL, added);
g_ptr_array_free(added, TRUE);
}
}
static void cell_info_dbus_cells_changed_cb(struct ofono_cell_info *info,
void *data)
{
DBG("");
cell_info_dbus_update_entries((CellInfoDBus *) data, TRUE);
}
static DBusMessage *cell_info_dbus_error_failed(DBusMessage *msg,
const char *explanation)
{
return g_dbus_create_error(msg, OFONO_ERROR_INTERFACE ".Failed", "%s",
explanation);
}
static DBusMessage *cell_info_dbus_get_cells(DBusConnection *conn,
DBusMessage *msg, void *data)
{
CellInfoDBus *dbus = data;
const char *sender = dbus_message_get_sender(msg);
if (ofono_dbus_clients_add(dbus->clients, sender)) {
DBusMessage *reply = dbus_message_new_method_return(msg);
DBusMessageIter it, a;
GSList *l;
ofono_cell_info_set_enabled(dbus->info, TRUE);
dbus_message_iter_init_append(reply, &it);
dbus_message_iter_open_container(&it, DBUS_TYPE_ARRAY, "o", &a);
for (l = dbus->entries; l; l = l->next) {
const CellEntry *entry = l->data;
dbus_message_iter_append_basic(&a,
DBUS_TYPE_OBJECT_PATH, &entry->path);
}
dbus_message_iter_close_container(&it, &a);
return reply;
}
return cell_info_dbus_error_failed(msg, "Operation failed");
}
static DBusMessage *cell_info_dbus_unsubscribe(DBusConnection *conn,
DBusMessage *msg, void *data)
{
CellInfoDBus *dbus = data;
const char *sender = dbus_message_get_sender(msg);
DBG("%s", sender);
if (ofono_dbus_clients_remove(dbus->clients, sender)) {
DBusMessage *signal = dbus_message_new_signal(dbus->path,
CELL_INFO_DBUS_INTERFACE,
CELL_INFO_DBUS_UNSUBSCRIBED_SIGNAL);
if (!ofono_dbus_clients_count(dbus->clients)) {
ofono_cell_info_set_enabled(dbus->info, FALSE);
}
dbus_message_set_destination(signal, sender);
g_dbus_send_message(dbus->conn, signal);
return dbus_message_new_method_return(msg);
}
return cell_info_dbus_error_failed(msg, "Not subscribed");
}
static const GDBusMethodTable cell_info_dbus_methods[] = {
{ GDBUS_METHOD("GetCells", NULL,
GDBUS_ARGS({ "paths", "ao" }),
cell_info_dbus_get_cells) },
{ GDBUS_METHOD("Unsubscribe", NULL, NULL,
cell_info_dbus_unsubscribe) },
{ }
};
static const GDBusSignalTable cell_info_dbus_signals[] = {
{ GDBUS_SIGNAL(CELL_INFO_DBUS_CELLS_ADDED_SIGNAL,
GDBUS_ARGS({ "paths", "ao" })) },
{ GDBUS_SIGNAL(CELL_INFO_DBUS_CELLS_REMOVED_SIGNAL,
GDBUS_ARGS({ "paths", "ao" })) },
{ GDBUS_SIGNAL(CELL_INFO_DBUS_UNSUBSCRIBED_SIGNAL,
GDBUS_ARGS({})) },
{ }
};
static void cell_info_dbus_disconnect_cb(const char *name, void *data)
{
CellInfoDBus *dbus = data;
if (!ofono_dbus_clients_count(dbus->clients)) {
ofono_cell_info_set_enabled(dbus->info, FALSE);
}
}
CellInfoDBus *cell_info_dbus_new(struct ofono_modem *modem,
struct ofono_cell_info *info)
{
if (modem && info) {
CellInfoDBus *dbus = g_new0(CellInfoDBus, 1);
DBG("%s", ofono_modem_get_path(modem));
dbus->path = g_strdup(ofono_modem_get_path(modem));
dbus->conn = dbus_connection_ref(ofono_dbus_get_connection());
dbus->info = ofono_cell_info_ref(info);
dbus->handler_id = ofono_cell_info_add_change_handler(info,
cell_info_dbus_cells_changed_cb, dbus);
/* Register D-Bus interface */
if (g_dbus_register_interface(dbus->conn, dbus->path,
CELL_INFO_DBUS_INTERFACE,
cell_info_dbus_methods,
cell_info_dbus_signals,
NULL, dbus, NULL)) {
ofono_modem_add_interface(modem,
CELL_INFO_DBUS_INTERFACE);
cell_info_dbus_update_entries(dbus, FALSE);
dbus->clients = ofono_dbus_clients_new(dbus->conn,
cell_info_dbus_disconnect_cb, dbus);
return dbus;
} else {
ofono_error("CellInfo D-Bus register failed");
cell_info_dbus_free(dbus);
}
}
return NULL;
}
void cell_info_dbus_free(CellInfoDBus *dbus)
{
if (dbus) {
GSList *l;
DBG("%s", dbus->path);
ofono_dbus_clients_free(dbus->clients);
g_dbus_unregister_interface(dbus->conn, dbus->path,
CELL_INFO_DBUS_INTERFACE);
/* Unregister cells */
l = dbus->entries;
while (l) {
CellEntry *entry = l->data;
g_dbus_unregister_interface(dbus->conn, entry->path,
CELL_DBUS_INTERFACE);
cell_info_destroy_entry(entry);
l = l->next;
}
g_slist_free(dbus->entries);
dbus_connection_unref(dbus->conn);
ofono_cell_info_remove_handler(dbus->info, dbus->handler_id);
ofono_cell_info_unref(dbus->info);
g_free(dbus->path);
g_free(dbus);
}
}
/*
* Local Variables:
* mode: C
* c-basic-offset: 8
* indent-tabs-mode: t
* End:
*/

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony - RIL-based devices
*
* Copyright (C) 2016-2017 Jolla Ltd.
* Copyright (C) 2016-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -13,19 +13,18 @@
* GNU General Public License for more details.
*/
#ifndef SAILFISH_CELL_INFO_DBUS_H
#define SAILFISH_CELL_INFO_DBUS_H
#ifndef CELL_INFO_DBUS_H
#define CELL_INFO_DBUS_H
struct ofono_modem;
struct ofono_cell_info;
struct sailfish_cell_info;
struct sailfish_cell_info_dbus;
struct cell_info_dbus;
struct cell_info_dbus *cell_info_dbus_new(struct ofono_modem *modem,
struct ofono_cell_info *ci);
void cell_info_dbus_free(struct cell_info_dbus *dbus);
struct sailfish_cell_info_dbus *sailfish_cell_info_dbus_new
(struct ofono_modem *modem, struct sailfish_cell_info *info);
void sailfish_cell_info_dbus_free(struct sailfish_cell_info_dbus *dbus);
#endif /* SAILFISH_CELL_INFO_DBUS_H */
#endif /* CELL_INFO_DBUS_H */
/*
* Local Variables:

View File

@@ -1,7 +1,7 @@
/*
* oFono - Open Source Telephony
*
* Copyright (C) 2017-2019 Jolla Ltd.
* Copyright (C) 2017-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -13,19 +13,17 @@
* GNU General Public License for more details.
*/
#include <sailfish_cell_info.h>
#include "ofono.h"
#include <gutil_log.h>
gint sailfish_cell_compare_location(const struct sailfish_cell *c1,
const struct sailfish_cell *c2)
int ofono_cell_compare_location(const struct ofono_cell *c1,
const struct ofono_cell *c2)
{
if (c1 && c2) {
if (c1->type != c2->type) {
return c1->type - c2->type;
} else if (c1->type == SAILFISH_CELL_TYPE_GSM) {
const struct sailfish_cell_info_gsm *g1;
const struct sailfish_cell_info_gsm *g2;
} else if (c1->type == OFONO_CELL_TYPE_GSM) {
const struct ofono_cell_info_gsm *g1;
const struct ofono_cell_info_gsm *g2;
g1 = &c1->info.gsm;
g2 = &c2->info.gsm;
@@ -38,9 +36,9 @@ gint sailfish_cell_compare_location(const struct sailfish_cell *c1,
} else {
return g1->cid - g2->cid;
}
} else if (c2->type == SAILFISH_CELL_TYPE_WCDMA) {
const struct sailfish_cell_info_wcdma *w1;
const struct sailfish_cell_info_wcdma *w2;
} else if (c1->type == OFONO_CELL_TYPE_WCDMA) {
const struct ofono_cell_info_wcdma *w1;
const struct ofono_cell_info_wcdma *w2;
w1 = &c1->info.wcdma;
w2 = &c2->info.wcdma;
@@ -53,13 +51,12 @@ gint sailfish_cell_compare_location(const struct sailfish_cell *c1,
} else {
return w1->cid - w2->cid;
}
} else {
const struct sailfish_cell_info_lte *l1 =
} else if (c1->type == OFONO_CELL_TYPE_LTE) {
const struct ofono_cell_info_lte *l1 =
&c1->info.lte;
const struct sailfish_cell_info_lte *l2 =
const struct ofono_cell_info_lte *l2 =
&c2->info.lte;
GASSERT(c1->type == SAILFISH_CELL_TYPE_LTE);
l1 = &c1->info.lte;
l2 = &c2->info.lte;
if (l1->mcc != l2->mcc) {
@@ -73,6 +70,9 @@ gint sailfish_cell_compare_location(const struct sailfish_cell *c1,
} else {
return l1->tac - l2->tac;
}
} else {
ofono_warn("Unexpected cell type");
return 0;
}
} else if (c1) {
return 1;
@@ -83,48 +83,48 @@ gint sailfish_cell_compare_location(const struct sailfish_cell *c1,
}
}
gint sailfish_cell_compare_func(gconstpointer v1, gconstpointer v2)
struct ofono_cell_info *ofono_cell_info_ref(struct ofono_cell_info *ci)
{
return sailfish_cell_compare_location(v1, v2);
}
struct sailfish_cell_info *sailfish_cell_info_ref
(struct sailfish_cell_info *info)
{
if (info) {
info->proc->ref(info);
return info;
if (ci && ci->proc->ref) {
ci->proc->ref(ci);
}
return NULL;
return ci;
}
void sailfish_cell_info_unref(struct sailfish_cell_info *info)
void ofono_cell_info_unref(struct ofono_cell_info *ci)
{
if (info) {
info->proc->unref(info);
if (ci && ci->proc->unref) {
ci->proc->unref(ci);
}
}
gulong sailfish_cell_info_add_cells_changed_handler
(struct sailfish_cell_info *info,
sailfish_cell_info_cb_t cb, void *arg)
unsigned long ofono_cell_info_add_change_handler(struct ofono_cell_info *ci,
ofono_cell_info_cb_t cb, void *data)
{
return info ? info->proc->add_cells_changed_handler(info, cb, arg) : 0;
return (ci && ci->proc->add_change_handler && cb) ?
ci->proc->add_change_handler(ci, cb, data) : 0;
}
void sailfish_cell_info_remove_handler(struct sailfish_cell_info *info,
gulong id)
void ofono_cell_info_remove_handler(struct ofono_cell_info *ci,
unsigned long id)
{
if (info) {
info->proc->remove_handler(info, id);
if (ci && ci->proc->remove_handler && id) {
ci->proc->remove_handler(ci, id);
}
}
void sailfish_cell_info_set_update_interval(struct sailfish_cell_info *info,
int ms)
void ofono_cell_info_set_update_interval(struct ofono_cell_info *ci, int ms)
{
if (info && info->proc->set_update_interval) {
info->proc->set_update_interval(info, ms);
if (ci && ci->proc->set_update_interval) {
ci->proc->set_update_interval(ci, ms);
}
}
void ofono_cell_info_set_enabled(struct ofono_cell_info *ci,
ofono_bool_t enabled)
{
if (ci && ci->proc->set_enabled) {
ci->proc->set_enabled(ci, enabled);
}
}

View File

@@ -3,6 +3,7 @@
* oFono - Open Source Telephony
*
* Copyright (C) 2008-2011 Intel Corporation. All rights reserved.
* Copyright (C) 2015-2021 Jolla Ltd.
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License version 2 as
@@ -29,7 +30,7 @@
#include <glib.h>
#include <ofono/types.h>
#include <ofono/misc.h>
#include <ofono/gprs-context.h>
#include "common.h"
#include "util.h"
@@ -422,10 +423,9 @@ int mmi_service_code_to_bearer_class(int code)
return cls;
}
const char *phone_number_to_string(const struct ofono_phone_number *ph)
const char *ofono_phone_number_to_string(const struct ofono_phone_number *ph,
char buffer[/* OFONO_MAX_PHONE_NUMBER_BUFFER_SIZE */])
{
static char buffer[OFONO_MAX_PHONE_NUMBER_LENGTH + 2];
if (ph->type == 145 && (strlen(ph->number) > 0) &&
ph->number[0] != '+') {
buffer[0] = '+';
@@ -439,6 +439,13 @@ const char *phone_number_to_string(const struct ofono_phone_number *ph)
return buffer;
}
const char *phone_number_to_string(const struct ofono_phone_number *ph)
{
static char buffer[OFONO_PHONE_NUMBER_BUFFER_SIZE];
return ofono_phone_number_to_string(ph, buffer);
}
void string_to_phone_number(const char *str, struct ofono_phone_number *ph)
{
if (str[0] == '+') {
@@ -654,7 +661,7 @@ const char *bearer_class_to_string(enum bearer_class cls)
return NULL;
}
const char *registration_status_to_string(int status)
const char *registration_status_to_string(enum ofono_netreg_status status)
{
switch (status) {
case NETWORK_REGISTRATION_STATUS_NOT_REGISTERED:
@@ -669,12 +676,14 @@ const char *registration_status_to_string(int status)
return "unknown";
case NETWORK_REGISTRATION_STATUS_ROAMING:
return "roaming";
case OFONO_NETREG_STATUS_NONE:
break;
}
return "";
}
const char *registration_tech_to_string(int tech)
const char *registration_tech_to_string(enum ofono_access_technology tech)
{
switch (tech) {
case ACCESS_TECHNOLOGY_GSM:
@@ -693,9 +702,10 @@ const char *registration_tech_to_string(int tech)
return "hspa";
case ACCESS_TECHNOLOGY_EUTRAN:
return "lte";
default:
return "";
case OFONO_ACCESS_TECHNOLOGY_NONE:
break;
}
return "";
}
gboolean is_valid_apn(const char *apn)
@@ -765,3 +775,15 @@ const char *call_status_to_string(enum call_status status)
return "unknown";
}
/* Public API exported to external plugins */
const char *ofono_netreg_status_to_string(enum ofono_netreg_status status)
{
return registration_status_to_string(status);
}
const char *ofono_access_technology_to_string(enum ofono_access_technology tech)
{
return registration_tech_to_string(tech);
}

Some files were not shown because too many files have changed in this diff Show More