Skip to contentSkip to conversation

MNC/MCC as string?

DISCUSSION Aki Niemi 5 participants 26 messages Jun 10, 2009 – Jun 13, 2009

lore
Share & tools
lore

Aki Niemi

author
#0 lore raw

Hi,

Currently, the MNC and MCC values are of type short, which is a little problematic.

The MNC code can either be 2 or 3 digits, and it would be quite natural to assume the logic is that 3 digits are used for codes > 99. However, this is not correct -- it depends on the MCC. It seems mostly American operators have 3 digit MNCs, whereas most of the rest of the world 2 digit MNCs. The implication is that 01 and 001 are not considered identical.

Nokia modems both send and receive MNC/MCC pairs as Binary Coded Decimal (BCD) strings. Any 2 digit MNC is padded with 0xF. Problem is, when listing operators, the conversion of MNC codes from BCD to short loses this information, and will result in manual network selection failing (BCD '001' -> short '1' -> BCD '01F' != BCD '001').

Anyone opposed to changing the mnc and mcc code types from short to string?

Cheers,
Aki

#1 lore raw

Aki,

Quoted 10 lines · On Wednesday 10 June 2009 06:26:07 Aki Niemi wrote:

Hi,

Currently, the MNC and MCC values are of type short, which is a little problematic.

The MNC code can either be 2 or 3 digits, and it would be quite natural to assume the logic is that 3 digits are used for codes > 99. However, this is not correct -- it depends on the MCC. It seems mostly American operators have 3 digit MNCs, whereas most of the rest of the world 2 digit MNCs. The implication is that 01 and 001 are not considered identical.

It doesn't seem this clear-cut. E.g. according to my Neo on with T-Mobile US SIM:

AT+COPS?
+COPS: 0,0,"T-Mobile"
OK
AT+COPS=3,2
OK
AT+COPS?
+COPS: 0,2,"31026"
OK
AT+COPS=2
OK
+CREG: 0
AT+COPS=1,2,"31026"
OK
+CREG: 2
+CREG: 1,"99EC","1A11"

At least according to wikipedia the real MCC/MNC of T-Mobile is 310260. Go figure.

Quoted 9 lines

Nokia modems both send and receive MNC/MCC pairs as Binary Coded Decimal (BCD) strings. Any 2 digit MNC is padded with 0xF. Problem is, when listing operators, the conversion of MNC codes from BCD to short loses this information, and will result in manual network selection failing (BCD '001' -> short '1' -> BCD '01F' != BCD '001').

Anyone opposed to changing the mnc and mcc code types from short to string?

I agree that this does seem to be an issue, so no problems in changing this. Do you consider this an implementation issue only (e.g. APIs do not change) or do you want to change the NetworkOperator attributes to a string as well? If this is an implementation issue we can always adopt the Nokia convention of padding the MNC by 0xF on the right and leave them as a 'short'.

Quoted 7 lines

Cheers,
Aki
_______________________________________________
ofono mailing list
ofono(a)ofono.org
http://lists.ofono.org/listinfo/ofono

Regards,
-Denis

#2 lore raw

Le mercredi 10 juin 2009 19:15:19 Denis Kenzior, vous avez écrit :

Quoted 9 lines
Quoted 8 lines

Nokia modems both send and receive MNC/MCC pairs as Binary Coded Decimal (BCD) strings. Any 2 digit MNC is padded with 0xF. Problem is, when listing operators, the conversion of MNC codes from BCD to short loses this information, and will result in manual network selection failing (BCD '001' -> short '1' -> BCD '01F' != BCD '001').

Anyone opposed to changing the mnc and mcc code types from short to string?

Quoted 6 lines

I agree that this does seem to be an issue, so no problems in changing this. Do you consider this an implementation issue only (e.g. APIs do not change) or do you want to change the NetworkOperator attributes to a string as well? If this is an implementation issue we can always adopt the Nokia convention of padding the MNC by 0xF on the right and leave them as a 'short'.

Well, the point is that leading zeroes are meaningful (much like with phone numbers in fact). The API, not just the implementation, must distinguish network "xy" from network "0xy", so that manual selection remains unambiguous. A D-Bus string is probably nicer to use than an integer using ISI's BCD scheme.

Signature · 2 lines
Rémi Denis-Courmont
Nokia Devices R&D
#3 lore raw

Hi Remi,

Well, the point is that leading zeroes are meaningful (much like with phone

Quoted 5 lines

numbers in fact). The API, not just the implementation, must distinguish network "xy" from network "0xy", so that manual selection remains unambiguous.
A D-Bus string is probably nicer to use than an integer using ISI's BCD scheme

I understand perfectly. But remember, oFono does not expose the user to such details. Manual registration is accomplished by using Register() method (with no arguments) of the NetworkOperator interface. The internal storage representation is never exposed. Thus it doesn't matter whether internally it is a string or short, etc.

The attributes are really only for informational purposes only. The user would not base his decision on the mcc/mnc, but on the operator name.

So before we start changing the D-Bus APIs, we need to answer these two questions:
- Can a country/administrative domain have both 001 and 01 MNCs such that
the use of string for the MNC is actually necessary.
- What does the user find easier to use, a string or a short?

Regards,
-Denis

#4 lore raw

Hi Denis,

Quoted 11 lines

I understand perfectly. But remember, oFono does not expose the user to such details. Manual registration is accomplished by using Register() method (with no arguments) of the NetworkOperator interface. The internal storage representation is never exposed. Thus it doesn't matter whether internally it is a string or short, etc.

The attributes are really only for informational purposes only. The user would not base his decision on the mcc/mnc, but on the operator name.

Quoted 5 lines

So before we start changing the D-Bus APIs, we need to answer these two questions:
- Can a country/administrative domain have both 001 and 01 MNCs such
that the use of string for the MNC is actually necessary.
- What does the user find easier to use, a string or a short?

I wasn't aware of this and so it might be better to just expose these as an operator id string. So we might not even split into MCC/MNC at all since it is meaning less anyway.

That said, we do want some exposure of these values since it is an easy way to determine geo location help and switch timezones etc. However I am now thinking that me might just add a Country property and do the proper translation inside oFono. Since we mostly care about these ones most.

Regards

Marcel

#5 lore raw
Quoted 12 lines · Marcel Holtmann

Hi Denis,

Quoted 9 lines

The attributes are really only for informational purposes only. The user would not base his decision on the mcc/mnc, but on the operator name.

So before we start changing the D-Bus APIs, we need to answer these two questions:
- Can a country/administrative domain have both 001 and 01 MNCs such
that the use of string for the MNC is actually necessary.
- What does the user find easier to use, a string or a short?

Quoted 3 lines

I wasn't aware of this and so it might be better to just expose these as an operator id string. So we might not even split into MCC/MNC at all since it is meaning less anyway.

This is probably the way to go...

Quoted 5 lines

That said, we do want some exposure of these values since it is an easy way to determine geo location help and switch timezones etc. However I am now thinking that me might just add a Country property and do the proper translation inside oFono. Since we mostly care about these ones most.

While inferring the country from MCC sounds nice, there are some corner cases where is causes problems:

Digicel Bermuda uses 310/38 (or 310/038?), 310 is the US MCC:
http://dougtoombs.com/2008/07/23/bermuda-the-iphone-and-att-beware-the-data-roaming/

Montenegro used MCC 220 (Serbia) before it switched to MCC 297.

Wikipedia has a list:
http://en.wikipedia.org/wiki/Mobile_Network_Code

If you plan to ship such a list with ofono, maybe
http://git.freesmartphone.org/?p=framework.git;a=blob;f=etc/freesmartphone/ogsmd/networks.tab
can be useful for you. OTOH, Nokia probably has a better list.

Jan

#6 lore raw

Hi Jan,

Quoted 28 lines
Quoted 10 lines
Quoted 9 lines

The attributes are really only for informational purposes only. The user would not base his decision on the mcc/mnc, but on the operator name.

So before we start changing the D-Bus APIs, we need to answer these two questions:
- Can a country/administrative domain have both 001 and 01 MNCs such
that the use of string for the MNC is actually necessary.
- What does the user find easier to use, a string or a short?

Quoted 3 lines

I wasn't aware of this and so it might be better to just expose these as an operator id string. So we might not even split into MCC/MNC at all since it is meaning less anyway.

This is probably the way to go...

Quoted 5 lines

That said, we do want some exposure of these values since it is an easy way to determine geo location help and switch timezones etc. However I am now thinking that me might just add a Country property and do the proper translation inside oFono. Since we mostly care about these ones most.

While inferring the country from MCC sounds nice, there are some corner cases where is causes problems:

Digicel Bermuda uses 310/38 (or 310/038?), 310 is the US MCC:
http://dougtoombs.com/2008/07/23/bermuda-the-iphone-and-att-beware-the-data-roaming/

Quoted 8 lines

Montenegro used MCC 220 (Serbia) before it switched to MCC 297.

Wikipedia has a list:
http://en.wikipedia.org/wiki/Mobile_Network_Code

If you plan to ship such a list with ofono, maybe
http://git.freesmartphone.org/?p=framework.git;a=blob;f=etc/freesmartphone/ogsmd/networks.tab
can be useful for you. OTOH, Nokia probably has a better list.

we will hide this minor defect inside the daemon and not bother the use with details.

Regards

Marcel

#7 lore raw
In reply to Marcel Holtmann

Hi Marcel,

Quoted 3 lines

I wasn't aware of this and so it might be better to just expose these as an operator id string. So we might not even split into MCC/MNC at all since it is meaning less anyway.

I'm tending to agree, which is why I wanted to start the conversation.

By the way, just so that we're all clear, here's the relevant quote from the standard:

"
MCC, Mobile country code (octet 2 and 3)
The MCC field is coded as in ITU-T Rec. E212, Annex A.

MNC, Mobile network code (octet 3 bits 5 to 8, octet 4)
The coding of this field is the responsibility of each administration but BCD coding shall be used. The MNC shall consist of 2 or 3 digits. For PCS 1900 for NA, Federal regulation mandates that a 3-digit MNC shall be used. However a network operator may decide to use only two digits in the MNC in the LAI over the radio interface. In this case, bits 5 to 8 of octet 3 shall be coded as "1111". Mobile equipment shall accept LAI coded in such a way.
"

Quoted 7 lines

That said, we do want some exposure of these values since it is an easy way to determine geo location help and switch timezones etc. However I am now thinking that me might just add a Country property and do the proper translation inside oFono. Since we mostly care about these ones most.

About the only thing that MCC/MNC is useful for is to display it during manual operator selection. MCC/MNC is not helpful at all for countries like U.S. with 4+ timezones and the same carrier id across all of them. A country property would work just as well for this. What standard do we want to use here? ITU 212? ISO 3166? or E164?

Any objections from actually removing the MCC/MNC Properties?

Regards,
-Denis

#8 lore raw

Hi Denis,

Quoted 30 lines
Quoted 3 lines

I wasn't aware of this and so it might be better to just expose these as an operator id string. So we might not even split into MCC/MNC at all since it is meaning less anyway.

I'm tending to agree, which is why I wanted to start the conversation.

By the way, just so that we're all clear, here's the relevant quote from the standard:

"
MCC, Mobile country code (octet 2 and 3)
The MCC field is coded as in ITU-T Rec. E212, Annex A.

MNC, Mobile network code (octet 3 bits 5 to 8, octet 4)
The coding of this field is the responsibility of each administration but BCD coding shall be used. The MNC shall consist of 2 or 3 digits. For PCS 1900 for NA, Federal regulation mandates that a 3-digit MNC shall be used. However a network operator may decide to use only two digits in the MNC in the LAI over the radio interface. In this case, bits 5 to 8 of octet 3 shall be coded as "1111". Mobile equipment shall accept LAI coded in such a way.
"

Quoted 7 lines

That said, we do want some exposure of these values since it is an easy way to determine geo location help and switch timezones etc. However I am now thinking that me might just add a Country property and do the proper translation inside oFono. Since we mostly care about these ones most.

Quoted 7 lines

About the only thing that MCC/MNC is useful for is to display it during manual operator selection. MCC/MNC is not helpful at all for countries like U.S. with 4+ timezones and the same carrier id across all of them. A country property would work just as well for this. What standard do we want to use here? ITU 212? ISO 3166? or E164?

Any objections from actually removing the MCC/MNC Properties?

you know what. Lets remove them now. If we figure out on how to make better use of them, we can add them later. Adding properties is way simpler than deprecating/removing or changing them.

For the country, I would prefer simple alpha2 encoding. That way this becomes similar to what WiFi uses for their regulatory enforcement.

Regards

Marcel

author
#9 lore raw
In reply to Denis Kenzior
Quoted 3 lines · Denis Kenzior

About the only thing that MCC/MNC is useful for is to display it during manual
operator selection.

That's not true. In fact, I'd say manual operator selection is just about the last
place where the codes should be displayed.

Quoted 3 lines

MCC/MNC is not helpful at all for countries like U.S.
with 4+ timezones and the same carrier id across all of them. A country property would work just as well for this.

For geolocation help, sure, but there are other places where MNC/MCC are used as keys to databases containing operator-specific information, like default Internet APN names and such.

Quoted 5 lines

What standard do we want to use

here? ITU 212? ISO 3166? or E164?

Any objections from actually removing the MCC/MNC Properties?

We need them.

Cheers,
Aki

#10 lore raw

Hi Aki,

Quoted 8 lines
Quoted 3 lines

About the only thing that MCC/MNC is useful for is to display it during manual
operator selection.

That's not true. In fact, I'd say manual operator selection is just about the last
place where the codes should be displayed.

Quoted 7 lines
Quoted 3 lines

MCC/MNC is not helpful at all for countries like U.S.
with 4+ timezones and the same carrier id across all of them. A country property would work just as well for this.

For geolocation help, sure, but there are other places where MNC/MCC are used as keys to databases containing operator-specific information, like default Internet APN names and such.

shouldn't we just integrate that database into oFono directly or as something like ofono-info.git that will be installed along with (for easier updates).

I know we need this database and mobilebroadband-providerinfo or similar project is doing this already.

Regards

Marcel

author
#11 lore raw
Quoted 7 lines · Marcel Holtmann
Quoted 3 lines

For geolocation help, sure, but there are other places where MNC/MCC are used as keys to databases containing operator-specific information, like default Internet APN names and such.

shouldn't we just integrate that database into oFono directly or as something like ofono-info.git that will be installed along with (for easier updates).

This particular database of default APN names, maybe, although I think it's really oFono users like Connman that should integrate with that information.

However, this wouldn't be the only database ever, so we would still need a way to reliably identify a specific operator.

Cheers,
Aki

#12 lore raw

Hi Aki,

Quoted 8 lines
Quoted 7 lines
Quoted 3 lines

For geolocation help, sure, but there are other places where MNC/MCC are used as keys to databases containing operator-specific information, like default Internet APN names and such.

shouldn't we just integrate that database into oFono directly or as something like ofono-info.git that will be installed along with (for easier updates).

Quoted 6 lines

This particular database of default APN names, maybe, although I think it's really oFono users like Connman that should integrate with that information.

However, this wouldn't be the only database ever, so we would still need a way to reliably identify a specific operator.

if we are unclear about the format and the users at this moment, I prefer we remove that interface and just keep it around as a TODO item to add it later.

As I said, adding something is easy, removing/deprecating hard and changing the format of it even harder.

Regards

Marcel

author
#13 lore raw
Quoted 5 lines · Marcel Holtmann
Quoted 3 lines

However, this wouldn't be the only database ever, so we would still need a
way to reliably identify a specific operator.

if we are unclear about the format and the users at this moment,

The format should be 's' in D-Bus and in struct ofono_network_operator:

   char mnc[4];
   char mcc[4];

And as for users, we need access to both MNC and MCC.

What part of this is unclear?

Cheers,
Aki

#14 lore raw

Aki,

Quoted 9 lines · On Thursday 11 June 2009 14:38:49 Aki Niemi wrote:

On Thu, 11 Jun 2009 21:18:02 +0200, Marcel Holtmann <[email protected]>

Quoted 5 lines · wrote:
Quoted 3 lines

However, this wouldn't be the only database ever, so we would still need a
way to reliably identify a specific operator.

if we are unclear about the format and the users at this moment,

Quoted 8 lines

The format should be 's' in D-Bus and in struct ofono_network_operator:

   char mnc[4];
   char mcc[4];

And as for users, we need access to both MNC and MCC.

What part of this is unclear?

Please submit a patch to the mailing list reflecting how you think it should be implemented. If it looks reasonable then I'll integrate it.

Regards,
-Denis

author
#15 lore raw
Quoted 5 lines · Denis Kenzior
Quoted 1 line

What part of this is unclear?

Please submit a patch to the mailing list reflecting how you think it should be
implemented. If it looks reasonable then I'll integrate it.

Uh. You know I am one of the co-maintainers here? ;)

Anyway, here it is. Please test; seems to work for me on my N95.

Cheers,
Aki

From 88e6a0a521c69913ab954e5a79f923b317d5ed26 Mon Sep 17 00:00:00 2001
From: Aki Niemi <[email protected]>
Date: Fri, 12 Jun 2009 10:02:52 +0300
Subject: [PATCH] Change MNC and MCC variable types to string

This is to make sure both 2 and 3-digit MNC values are correctly handled. Both the modem plugin API as well as the D-Bus API are affected.

---
 drivers/atmodem/network-registration.c |   51 +++++++++++++------------------
 src/driver.h                           |    4 +-
 src/network.c                          |   48 ++++++++++++------------------
 3 files changed, 42 insertions(+), 61 deletions(-)
drivers/atmodem/network-registration.c +21 -30
index 40796d5..f73bb7c 100644
@@ -45,28 +45,18 @@ static const char *csq_prefix[] = { "+CSQ:", NULL };
 
 struct netreg_data {
 	gboolean supports_tech;
-	short mnc;
-	short mcc;
+	char mnc[4];
+	char mcc[4];
 };
 
-static void extract_mcc_mnc(const char *str, short *mcc, short *mnc)
+static void extract_mcc_mnc(const char *str, char *mcc, char *mnc)
 {
-	int num = 0;
-	unsigned int i;
-
 	/* Three digit country code */
-	for (i = 0; i < 3; i++)
-		num = num * 10 + (int)(str[i] - '0');
-
-	*mcc = num;
-
-	num = 0;
+	strncpy(mcc, str, sizeof(mcc));
+	mcc[3] = '\0';
 
 	/* Usually a 2 but sometimes 3 digit network code */
-	for (; i < strlen(str); i++)
-		num = num * 10 + (int)(str[i] - '0');
-
-	*mnc = num;
+	strncpy(mnc, str + 3, sizeof(mnc));
 }
 
 static void at_creg_cb(gboolean ok, GAtResult *result, gpointer user_data)
@@ -154,7 +144,7 @@ static void cops_cb(gboolean ok, GAtResult *result, gpointer user_data)
 	dump_response("cops_cb", ok, result);
 	decode_at_error(&error, g_at_result_final_response(result));
 
-	if (!ok || at->netreg->mcc == -1 || at->netreg->mnc == -1) {
+	if (!ok || *at->netreg->mcc == '\0' || *at->netreg->mnc == '\0') {
 		cb(&error, NULL, cbd->data);
 		goto out;
 	}
@@ -181,12 +171,12 @@ static void cops_cb(gboolean ok, GAtResult *result, gpointer user_data)
 	strncpy(op.name, name, OFONO_MAX_OPERATOR_NAME_LENGTH);
 	op.name[OFONO_MAX_OPERATOR_NAME_LENGTH] = '\0';
 
-	op.mcc = at->netreg->mcc;
-	op.mnc = at->netreg->mnc;
+	strncpy(op.mcc, at->netreg->mcc, sizeof(op.mcc));
+	strncpy(op.mnc, at->netreg->mnc, sizeof(op.mnc));
 	op.status = -1;
 	op.tech = tech;
 
-	ofono_debug("cops_cb: %s, %hd %hd %d", name, at->netreg->mcc,
+	ofono_debug("cops_cb: %s, %s %s %d", name, at->netreg->mcc,
 			at->netreg->mnc, tech);
 
 	cb(&error, &op, cbd->data);
@@ -235,15 +225,16 @@ static void cops_numeric_cb(gboolean ok, GAtResult *result, gpointer user_data)
 		strlen(str) == 0)
 		goto error;
 
-	extract_mcc_mnc(str, &at->netreg->mcc, &at->netreg->mnc);
+	extract_mcc_mnc(str, at->netreg->mcc, at->netreg->mnc);
 
-	ofono_debug("Cops numeric got mcc: %hd, mnc: %hd",
+	ofono_debug("Cops numeric got mcc: %s, mnc: %s",
 			at->netreg->mcc, at->netreg->mnc);
 
 	return;
 
 error:
-	at->netreg->mcc = at->netreg->mnc = -1;
+	*at->netreg->mcc = '\0';
+	*at->netreg->mnc = '\0';
 }
 
 static void at_current_operator(struct ofono_modem *modem,
@@ -356,7 +347,7 @@ static void cops_list_cb(gboolean ok, GAtResult *result, gpointer user_data)
 			if (!g_at_result_iter_next_string(&iter, &n))
 				break;
 
-			extract_mcc_mnc(n, &list[num].mcc, &list[num].mnc);
+			extract_mcc_mnc(n, list[num].mcc, list[num].mnc);
 
 			if (!g_at_result_iter_next_number(&iter, &tech))
 				tech = 0;
@@ -376,7 +367,7 @@ static void cops_list_cb(gboolean ok, GAtResult *result, gpointer user_data)
 	int i = 0;
 
 	for (; i < num; i++) {
-		ofono_debug("Operator: %s, %hd, %hd, status: %d, %d",
+		ofono_debug("Operator: %s, %s, %s, status: %d, %d",
 				list[i].name, list[i].mcc, list[i].mnc,
 				list[i].status, list[i].tech);
 	}
@@ -457,12 +448,12 @@ static void at_register_manual(struct ofono_modem *modem,
 		goto error;
 
 	if (at->netreg->supports_tech && oper->tech != -1)
-		sprintf(buf, "AT+COPS=1,2,\"%03hd%02hd\",%1d", oper->mcc,
-							oper->mnc,
-							oper->tech);
+		sprintf(buf, "AT+COPS=1,2,\"%s%s\",%1d", oper->mcc,
+						oper->mnc,
+						oper->tech);
 	else
-		sprintf(buf, "AT+COPS=1,2,\"%03hd%02hd\"", oper->mcc,
-							oper->mnc);
+		sprintf(buf, "AT+COPS=1,2,\"%s%s\"", oper->mcc,
+						oper->mnc);
 
 	if (g_at_chat_send(at->parser, buf, none_prefix,
 				register_cb, cbd, g_free) > 0)
src/driver.h +2 -2
index 61504dd..33b7586 100644
@@ -76,8 +76,8 @@ struct ofono_call {
 
 struct ofono_network_operator {
 	char name[OFONO_MAX_OPERATOR_NAME_LENGTH + 1];
-	short mcc;
-	short mnc;
+	char mcc[4];
+	char mnc[4];
 	int status;
 	int tech;
 };
src/network.c +19 -29

97 lines not on this page · raw message

Signature · 1 line
1.6.0.4
#16 lore raw

Hi Aki,

Quoted 1 line

Anyway, here it is. Please test; seems to work for me on my N95.

+static void extract_mcc_mnc(const char *str, char *mcc, char *mnc)
{
- int num = 0;
- unsigned int i;
-

        /* Three digit country code */

- for (i = 0; i < 3; i++)
- num = num * 10 + (int)(str[i] - '0');
-
- *mcc = num;
-

-       num = 0;
+       strncpy(mcc, str, sizeof(mcc));
+       mcc[3] = '\0';

maybe I am blind, but how is this suppose to work. The sizeof(mmc) is 1 byte.

Regards

Marcel

author
#17 lore raw
Quoted 5 lines · Marcel Holtmann
(quoted diff) +2 -0
+       strncpy(mcc, str, sizeof(mcc));
+       mcc[3] = '\0';

maybe I am blind, but how is this suppose to work. The sizeof(mmc) is 1 byte.

Actually, sizeof(mmc) is 4 bytes. Coincidentally, so is the char array in mcc. ;)

Take two attached.

Cheers,
Aki

From 5ea55baef4a10b3977675284c83d21e0a8f54a7b Mon Sep 17 00:00:00 2001
From: Aki Niemi <[email protected]>
Date: Fri, 12 Jun 2009 10:02:52 +0300
Subject: [PATCH] Change MNC and MCC variable types to string

This is to make sure both 2 and 3-digit MNC values are correctly handled. Both the modem plugin API as well as the D-Bus API are affected.

---
 drivers/atmodem/network-registration.c |   57 +++++++++++++++-----------------
 src/driver.h                           |    7 +++-
 src/network.c                          |   48 ++++++++++----------------
 3 files changed, 51 insertions(+), 61 deletions(-)
drivers/atmodem/network-registration.c +27 -30
index 40796d5..30dd0f7 100644
@@ -45,28 +45,20 @@ static const char *csq_prefix[] = { "+CSQ:", NULL };
 
 struct netreg_data {
 	gboolean supports_tech;
-	short mnc;
-	short mcc;
+	char mnc[OFONO_MAX_MNC_MCC_LENGTH + 1];
+	char mcc[OFONO_MAX_MNC_MCC_LENGTH + 1];
 };
 
-static void extract_mcc_mnc(const char *str, short *mcc, short *mnc)
+static void extract_mcc_mnc(const char *str, char *mcc, char *mnc)
 {
-	int num = 0;
-	unsigned int i;
-
 	/* Three digit country code */
-	for (i = 0; i < 3; i++)
-		num = num * 10 + (int)(str[i] - '0');
-
-	*mcc = num;
-
-	num = 0;
+	strncpy(mcc, str, OFONO_MAX_MNC_MCC_LENGTH);
+	mcc[OFONO_MAX_MNC_MCC_LENGTH] = '\0';
 
 	/* Usually a 2 but sometimes 3 digit network code */
-	for (; i < strlen(str); i++)
-		num = num * 10 + (int)(str[i] - '0');
-
-	*mnc = num;
+	strncpy(mnc, str + OFONO_MAX_MNC_MCC_LENGTH,
+		OFONO_MAX_MNC_MCC_LENGTH);
+	mnc[OFONO_MAX_MNC_MCC_LENGTH] = '\0';
 }
 
 static void at_creg_cb(gboolean ok, GAtResult *result, gpointer user_data)
@@ -154,7 +146,7 @@ static void cops_cb(gboolean ok, GAtResult *result, gpointer user_data)
 	dump_response("cops_cb", ok, result);
 	decode_at_error(&error, g_at_result_final_response(result));
 
-	if (!ok || at->netreg->mcc == -1 || at->netreg->mnc == -1) {
+	if (!ok || *at->netreg->mcc == '\0' || *at->netreg->mnc == '\0') {
 		cb(&error, NULL, cbd->data);
 		goto out;
 	}
@@ -181,12 +173,16 @@ static void cops_cb(gboolean ok, GAtResult *result, gpointer user_data)
 	strncpy(op.name, name, OFONO_MAX_OPERATOR_NAME_LENGTH);
 	op.name[OFONO_MAX_OPERATOR_NAME_LENGTH] = '\0';
 
-	op.mcc = at->netreg->mcc;
-	op.mnc = at->netreg->mnc;
+	strncpy(op.mcc, at->netreg->mcc, OFONO_MAX_MNC_MCC_LENGTH);
+	op.mcc[OFONO_MAX_MNC_MCC_LENGTH] = '\0';
+
+	strncpy(op.mnc, at->netreg->mnc, OFONO_MAX_MNC_MCC_LENGTH);
+	op.mnc[OFONO_MAX_MNC_MCC_LENGTH] = '\0';
+
 	op.status = -1;
 	op.tech = tech;
 
-	ofono_debug("cops_cb: %s, %hd %hd %d", name, at->netreg->mcc,
+	ofono_debug("cops_cb: %s, %s %s %d", name, at->netreg->mcc,
 			at->netreg->mnc, tech);
 
 	cb(&error, &op, cbd->data);
@@ -235,15 +231,16 @@ static void cops_numeric_cb(gboolean ok, GAtResult *result, gpointer user_data)
 		strlen(str) == 0)
 		goto error;
 
-	extract_mcc_mnc(str, &at->netreg->mcc, &at->netreg->mnc);
+	extract_mcc_mnc(str, at->netreg->mcc, at->netreg->mnc);
 
-	ofono_debug("Cops numeric got mcc: %hd, mnc: %hd",
+	ofono_debug("Cops numeric got mcc: %s, mnc: %s",
 			at->netreg->mcc, at->netreg->mnc);
 
 	return;
 
 error:
-	at->netreg->mcc = at->netreg->mnc = -1;
+	*at->netreg->mcc = '\0';
+	*at->netreg->mnc = '\0';
 }
 
 static void at_current_operator(struct ofono_modem *modem,
@@ -356,7 +353,7 @@ static void cops_list_cb(gboolean ok, GAtResult *result, gpointer user_data)
 			if (!g_at_result_iter_next_string(&iter, &n))
 				break;
 
-			extract_mcc_mnc(n, &list[num].mcc, &list[num].mnc);
+			extract_mcc_mnc(n, list[num].mcc, list[num].mnc);
 
 			if (!g_at_result_iter_next_number(&iter, &tech))
 				tech = 0;
@@ -376,7 +373,7 @@ static void cops_list_cb(gboolean ok, GAtResult *result, gpointer user_data)
 	int i = 0;
 
 	for (; i < num; i++) {
-		ofono_debug("Operator: %s, %hd, %hd, status: %d, %d",
+		ofono_debug("Operator: %s, %s, %s, status: %d, %d",
 				list[i].name, list[i].mcc, list[i].mnc,
 				list[i].status, list[i].tech);
 	}
@@ -457,12 +454,12 @@ static void at_register_manual(struct ofono_modem *modem,
 		goto error;
 
 	if (at->netreg->supports_tech && oper->tech != -1)
-		sprintf(buf, "AT+COPS=1,2,\"%03hd%02hd\",%1d", oper->mcc,
-							oper->mnc,
-							oper->tech);
+		sprintf(buf, "AT+COPS=1,2,\"%s%s\",%1d", oper->mcc,
+						oper->mnc,
+						oper->tech);
 	else
-		sprintf(buf, "AT+COPS=1,2,\"%03hd%02hd\"", oper->mcc,
-							oper->mnc);
+		sprintf(buf, "AT+COPS=1,2,\"%s%s\"", oper->mcc,
+						oper->mnc);
 
 	if (g_at_chat_send(at->parser, buf, none_prefix,
 				register_cb, cbd, g_free) > 0)
src/driver.h +5 -2
index 61504dd..f753c7f 100644
@@ -74,10 +74,13 @@ struct ofono_call {
  *   */
 #define OFONO_MAX_OPERATOR_NAME_LENGTH 63
 
+/* MCC is always three digits. MNC is either two or three digits */
+#define OFONO_MAX_MNC_MCC_LENGTH 3
+
 struct ofono_network_operator {
 	char name[OFONO_MAX_OPERATOR_NAME_LENGTH + 1];
-	short mcc;
-	short mnc;
+	char mcc[OFONO_MAX_MNC_MCC_LENGTH + 1];
+	char mnc[OFONO_MAX_MNC_MCC_LENGTH + 1];
 	int status;
 	int tech;
 };
src/network.c +19 -29

97 lines not on this page · raw message

Signature · 1 line
1.6.0.4
#18 lore raw

Hi Aki,

Quoted 1 line

Take two attached.

I've pushed the patch out as well as an addendum patch that took care of some new and existing style issues. Also a small fix to the test case as a result of the API changes.

Regards,
-Denis

#19 lore raw
In reply to Marcel Holtmann
Quoted 19 lines · Marcel Holtmann

Hi Aki,

Quoted 1 line

Anyway, here it is. Please test; seems to work for me on my N95.

drivers/atmodem/network-registration.c +3 -9
+static void extract_mcc_mnc(const char *str, char *mcc, char *mnc)
 {
-       int num = 0;
-       unsigned int i;
-
        /* Three digit country code */
-       for (i = 0; i < 3; i++)
-               num = num * 10 + (int)(str[i] - '0');
-
-       *mcc = num;
-
-       num = 0;
+       strncpy(mcc, str, sizeof(mcc));
+       mcc[3] = '\0';
Quoted 2 lines

maybe I am blind, but how is this suppose to work. The sizeof(mmc) is 1 byte.

Actually, it is the size of a pointer, which will work (by accident) on 32-bits platform, and overflow on others.

Signature · 1 line
Rémi Denis-Courmont
#20 lore raw
In reply to Marcel Holtmann

Le jeudi 11 juin 2009 22:18:02 Marcel Holtmann, vous avez écrit :

Quoted 14 lines

Hi Aki,

Quoted 12 lines
Quoted 7 lines
Quoted 3 lines

For geolocation help, sure, but there are other places where MNC/MCC are used as keys to databases containing operator-specific information, like default Internet APN names and such.

shouldn't we just integrate that database into oFono directly or as something like ofono-info.git that will be installed along with (for easier updates).

This particular database of default APN names, maybe, although I think it's really oFono users like Connman that should integrate with that information.

Quoted 6 lines
Quoted 2 lines

However, this wouldn't be the only database ever, so we would still need a way to reliably identify a specific operator.

if we are unclear about the format and the users at this moment, I prefer we remove that interface and just keep it around as a TODO item to add it later.

I don't see any lack of clarity. It is a series of two or three digits.

Anyway, if the database has a hole, we probably will have to return the MNC/MCC anyway (ever tried scanning for network with an old phone in a foreign country?). Then there is also the uniqueness problem. MNC/MCC pair solves that.

Signature · 2 lines
Rémi Denis-Courmont
http://www.remlab.net/
#21 lore raw

Hi Remi,

Quoted 19 lines
Quoted 12 lines
Quoted 12 lines
Quoted 7 lines
Quoted 3 lines

For geolocation help, sure, but there are other places where MNC/MCC are used as keys to databases containing operator-specific information, like default Internet APN names and such.

shouldn't we just integrate that database into oFono directly or as something like ofono-info.git that will be installed along with (for easier updates).

This particular database of default APN names, maybe, although I think it's really oFono users like Connman that should integrate with that information.

Quoted 6 lines
Quoted 2 lines

However, this wouldn't be the only database ever, so we would still need a way to reliably identify a specific operator.

if we are unclear about the format and the users at this moment, I prefer we remove that interface and just keep it around as a TODO item to add it later.

Quoted 6 lines

I don't see any lack of clarity. It is a series of two or three digits.

Anyway, if the database has a hole, we probably will have to return the MNC/MCC anyway (ever tried scanning for network with an old phone in a foreign country?). Then there is also the uniqueness problem. MNC/MCC pair solves that.

if the database has a whole or we don't have the network provider string then we can just show the MNC/MCC in that case. That is pretty simple. No need to put extra burden into the userspace application and have it looking for two strings.

I don't understand your uniqueness issue. We will have unique object path for every network. What else does userspace needs?

Regards

Marcel

#22 lore raw
In reply to Aki Niemi

Hi Aki,

Quoted 8 lines
Quoted 7 lines
Quoted 3 lines

For geolocation help, sure, but there are other places where MNC/MCC are used as keys to databases containing operator-specific information, like default Internet APN names and such.

shouldn't we just integrate that database into oFono directly or as something like ofono-info.git that will be installed along with (for easier updates).

Quoted 6 lines

This particular database of default APN names, maybe, although I think it's really oFono users like Connman that should integrate with that information.

However, this wouldn't be the only database ever, so we would still need a way to reliably identify a specific operator.

I agree that there might be at some point a need for it, but what I question is the need for it right now. Do we have direct users in userspace that can make use of this information? Giving them directly to the user makes no sense.

Regards

Marcel

#23 lore raw
In reply to Aki Niemi

Aki,

Quoted 10 lines · On Thursday 11 June 2009 13:00:48 Aki Niemi wrote:

On Thu, 11 Jun 2009 09:32:38 -0500, Denis Kenzior <[email protected]>

Quoted 3 lines · wrote:

About the only thing that MCC/MNC is useful for is to display it during manual
operator selection.

That's not true. In fact, I'd say manual operator selection is just about the last
place where the codes should be displayed.

The point is MCCMNC is not something the user should realy be exposed to. It is useful to dis-ambiguate the carrier by Country when you're in a border area, but that is about it. Country property can do this just as well.

Quoted 9 lines
Quoted 4 lines

MCC/MNC is not helpful at all for countries like U.S.
with 4+ timezones and the same carrier id across all of them. A country property would work just as well for this.

For geolocation help, sure, but there are other places where MNC/MCC are used as keys to databases containing operator-specific information, like default Internet APN names and such.

Then lets design this into oFono instead of exposing an obscure attribute.

Regards,
-Denis

author
#24 lore raw
In reply to Marcel Holtmann
Quoted 2 lines · Marcel Holtmann

That said, we do want some exposure of these values since it is an easy way to determine geo location help and switch timezones etc.

For geolocation, cell ID and LAC are more useful, especially coupled with information on neighboring cells, RTT measurements, etc. We will probably need to expose this information some way.

Also, typically networks provide date-time, timezone and DST information via NITZ [1].

Cheers,
Aki

[1] http://en.wikipedia.org/wiki/NITZ

author
#25 lore raw
In reply to Denis Kenzior
Quoted 1 line · Denis Kenzior

It doesn't seem this clear-cut. E.g. according to my Neo on with

T-Mobile

Quoted 19 lines

US
SIM:

AT+COPS?
+COPS: 0,0,"T-Mobile"
OK
AT+COPS=3,2
OK
AT+COPS?
+COPS: 0,2,"31026"
OK
AT+COPS=2
OK
+CREG: 0
AT+COPS=1,2,"31026"
OK

(quoted diff) +2 -0
+CREG: 2
+CREG: 1,"99EC","1A11"
Quoted 1 line

At least according to wikipedia the real MCC/MNC of T-Mobile is 310260.

Go

Quoted 2 lines

figure.

I think this might be a separate issue with some North American operators that seem to pad also 3-digit codes, effectively dropping that trailing zero. Perhaps this is for legacy reasons.

Quoted 8 lines
Quoted 8 lines

Nokia modems both send and receive MNC/MCC pairs as Binary Coded Decimal (BCD) strings. Any 2 digit MNC is padded with 0xF. Problem is, when listing
operators, the conversion of MNC codes from BCD to short loses this information, and will result in manual network selection failing (BCD '001'
-> short '1' -> BCD '01F' != BCD '001').

Quoted 7 lines
Quoted 3 lines

Anyone opposed to changing the mnc and mcc code types from short to string?

I agree that this does seem to be an issue, so no problems in changing this.
Do you consider this an implementation issue only (e.g. APIs do not

change)

Quoted 2 lines

or
do you want to change the NetworkOperator attributes to a string as well?

I would go ahead and change them as well. In theory, there could exist both 2- and 3-digit MNCs within a single MCC, for which having strings is the safest option.

Cheers,
Aki