Skip to content
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.

Commit 7f7774a

Browse files
committedJan 29, 2015
binary DB backup, checkDBe and added OCID property
- Completed amisicd.db binary backup to "aimsicd_dump.db" on the SD card AIMSICD directory using the sqlite3 binary, assumed to be in: /system/xbin. - Added several DBe LAC/CIDconsistency checks via checkDBe() - Added a Boolean (true/false) system property (using native SU) to show if OCID data has been downloaded. Check with: "getprop aimsicd.ocid_downloaded" - Added new columns to opencellid (DBe_import) table: "avg_range, isGPSexact, Type"
1 parent 32194c6 commit 7f7774a

File tree

4 files changed

+192
-49
lines changed

4 files changed

+192
-49
lines changed
 

‎app/src/main/AndroidManifest.xml

+1-1
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@
22
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
33
package="com.SecUpwN.AIMSICD"
44
android:versionCode="25"
5-
android:versionName="0.1.25-alpha-b25">
5+
android:versionName="0.1.25-alpha-b26">
66

77
<!-- PERMISSIONS ARE SORTED BY TYPE - PLEASE KEEP THIS STRUCTURE. THANK YOU. /> -->
88

‎app/src/main/java/com/SecUpwN/AIMSICD/adapters/AIMSICDDbAdapter.java

+160-46
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22

33
import com.SecUpwN.AIMSICD.AIMSICD;
44
import com.SecUpwN.AIMSICD.utils.Cell;
5+
import com.SecUpwN.AIMSICD.utils.CMDProcessor;
56

67
import android.content.ContentValues;
78
import android.content.Context;
@@ -275,8 +276,19 @@ public long insertCell(Cell cell) {
275276
* TODO: Is this where CSV data is populating the opencellid table?
276277
*
277278
*/
278-
long insertOpenCell(double latitude, double longitude, int mcc, int mnc, int lac,
279-
int cellID, int avgSigStr, int samples) {
279+
long insertOpenCell(double latitude,
280+
double longitude,
281+
int mcc,
282+
int mnc,
283+
int lac,
284+
int cellID,
285+
int avgSigStr,
286+
int range, // new
287+
int samples,
288+
int isGPSexact, // new
289+
String RAT // new
290+
//int rej_cause // new
291+
) {
280292

281293
//Populate Content Values for Insert or Update
282294
ContentValues cellIDValues = new ContentValues();
@@ -287,8 +299,11 @@ long insertOpenCell(double latitude, double longitude, int mcc, int mnc, int lac
287299
cellIDValues.put("Lac", lac);
288300
cellIDValues.put("CellID", cellID);
289301
cellIDValues.put("AvgSigStr", avgSigStr);
290-
//cellIDValues.put("Range", range );
302+
cellIDValues.put("avg_range", range ); // new
291303
cellIDValues.put("Samples", samples);
304+
cellIDValues.put("isGPSexact", isGPSexact ); // new
305+
cellIDValues.put("Type", RAT ); // new
306+
//cellIDValues.put("rej_cause", rej_cause ); // new
292307

293308
if (openCellExists(cellID)) {
294309
Log.v(TAG, "CID already in OCID DB (db update): " + cellID);
@@ -415,10 +430,20 @@ public Cursor getLocationData() {
415430

416431
/**
417432
* Returns OpenCellID (DBe_import) database contents
433+
*
434+
* TODO: Need to implement new items!!
435+
* URGENT: Maybe not so urgent, but need looking after, since we added items.
436+
*
437+
* Used in:
438+
* DbViewerFragment.java
439+
* MapViewerOsmDroid.java
440+
*
441+
*
418442
*/
419443
public Cursor getOpenCellIDData() {
420444
return mDb.query( OPENCELLID_TABLE,
421445
new String[]{"CellID", "Lac", "Mcc", "Mnc", "Lat", "Lng", "AvgSigStr", "Samples"},
446+
// avg_range, rej_cause, Type
422447
null, null, null, null, null
423448
);
424449
}
@@ -458,7 +483,7 @@ boolean cellExists(int cellID) {
458483
Cursor cursor = mDb.rawQuery("SELECT 1 FROM " + CELL_TABLE +
459484
" WHERE CellID = " + cellID, null);
460485
boolean exists = cursor.getCount() > 0;
461-
Log.i(TAG, "Cell exists in local DB?: " + exists);
486+
Log.v(TAG, "CID: "+ cellID + " exists in local DB (DBi_bts) ?: " + exists);
462487
cursor.close();
463488
return exists;
464489
}
@@ -471,7 +496,7 @@ public boolean openCellExists(int cellID) {
471496
Cursor cursor = mDb.rawQuery("SELECT * FROM " + OPENCELLID_TABLE +
472497
" WHERE CellID = " + cellID, null);
473498
boolean exists = cursor.getCount() > 0;
474-
Log.i(TAG, "Cell exists in OCID?: " + exists);
499+
Log.v(TAG, "CID: " + cellID + " exists in OCID (DBe_import)?: " + exists);
475500
cursor.close();
476501
return exists;
477502
}
@@ -643,12 +668,21 @@ private void populateDefaultMCC(SQLiteDatabase db) {
643668
* Description: Parses the downloaded CSV from OpenCellID and uses it to populate "DBe_import".
644669
* ("opencellid" table.)
645670
*
671+
*
672+
* Dependency: RequestTask.java :: onPostExecute()
673+
* insertOpenCell()
646674
* Issues:
647675
*
648-
* [ ] Why are we only populating 8 items out of 19?
676+
* [ ] Progress is not shown or is the operation too quick?
649677
*
678+
* [ ] Why are we only populating 8 items out of 19?
650679
* From downloaded OCID CSV file: (19 items)
651680
*
681+
* NOTES:
682+
*
683+
* a) We do not include "rej_cause" in backups.
684+
* b)
685+
*
652686
* # head -2 opencellid.csv
653687
* lat,lon,mcc,mnc,lac,cellid,averageSignalStrength,range,samples,changeable,radio,rnc,cid,psc,tac,pci,sid,nid,bid
654688
* 54.63376,25.160243,246,3,20,1294,0,-1,1,1,GSM,,,,,,,,
@@ -676,6 +710,7 @@ public boolean updateOpenCellID() {
676710
int count = 0;
677711
AIMSICD.mProgressBar.setProgress(0);
678712
AIMSICD.mProgressBar.setMax(csvCellID.size());
713+
Log.i(TAG, "updateOpenCellID: OCID CSV size (lines?): " + csvCellID.size() );
679714
while ((next = csvReader.readNext()) != null) {
680715
csvCellID.add(next);
681716
AIMSICD.mProgressBar.setProgress(count++);
@@ -687,7 +722,7 @@ public boolean updateOpenCellID() {
687722
for (int i = 1; i < lines; i++) {
688723
AIMSICD.mProgressBar.setProgress(i);
689724

690-
// Insert details into OpenCellID Database
725+
// Insert details into OpenCellID Database using: insertOpenCell()
691726
// Beware of negative values of "range" and "samples"!!
692727
insertOpenCell( Double.parseDouble(csvCellID.get(i)[0]), // gps_lat
693728
Double.parseDouble(csvCellID.get(i)[1]), // gps_lon
@@ -696,10 +731,10 @@ public boolean updateOpenCellID() {
696731
Integer.parseInt(csvCellID.get(i)[4]), // LAC
697732
Integer.parseInt(csvCellID.get(i)[5]), // CID (cellid) ?
698733
Integer.parseInt(csvCellID.get(i)[6]), // avg_signal [dBm]
699-
//Integer.parseInt(csvCellID.get(i)[7]), // avg_range [m]
700-
Integer.parseInt(csvCellID.get(i)[8]) // samples
701-
//Integer.parseInt(csvCellID.get(i)[9]), // isGPSexact
702-
//Integer.parseInt(csvCellID.get(i)[10]), // RAT
734+
Integer.parseInt(csvCellID.get(i)[7]), // avg_range [m]
735+
Integer.parseInt(csvCellID.get(i)[8]), // samples
736+
Integer.parseInt(csvCellID.get(i)[9]), // isGPSexact
737+
String.valueOf(csvCellID.get(i)[10]) // RAT
703738
//Integer.parseInt(csvCellID.get(i)[11]), // --- RNC
704739
//Integer.parseInt(csvCellID.get(i)[12]), // --- (cid) ?
705740
//Integer.parseInt(csvCellID.get(i)[13]), // --- PSC
@@ -783,14 +818,20 @@ public boolean restoreDB() {
783818

784819
case OPENCELLID_TABLE:
785820
insertOpenCell(
786-
Double.parseDouble(records.get(i)[1]), //
787-
Double.parseDouble(records.get(i)[2]), //
788-
Integer.parseInt(records.get(i)[3]), //
789-
Integer.parseInt(records.get(i)[4]), //
790-
Integer.parseInt(records.get(i)[5]), //
791-
Integer.parseInt(records.get(i)[6]), //
792-
Integer.parseInt(records.get(i)[7]), //
793-
Integer.parseInt(records.get(i)[8])); //
821+
// not sure about the naming of these, need CHECK!
822+
Double.parseDouble(records.get(i)[1]), // lat
823+
Double.parseDouble(records.get(i)[2]), // lng
824+
Integer.parseInt(records.get(i)[3]), // mcc
825+
Integer.parseInt(records.get(i)[4]), // mnc
826+
Integer.parseInt(records.get(i)[5]), // lac
827+
Integer.parseInt(records.get(i)[6]), // cid
828+
Integer.parseInt(records.get(i)[7]), // avg_sig..
829+
Integer.parseInt(records.get(i)[8]), // ); range
830+
Integer.parseInt(records.get(i)[9]), // new samples
831+
Integer.parseInt(records.get(i)[10]), // new isGPSexact
832+
String.valueOf(records.get(i)[11]) // new RAT
833+
//Integer.parseInt(records.get(i)[10]), // new rej_cause
834+
);
794835
break;
795836

796837
case SILENT_SMS_TABLE:
@@ -840,19 +881,28 @@ public boolean restoreDB() {
840881
* @return
841882
*/
842883
private void dumpDB() {
843-
File dir = new File(FOLDER);
884+
File dumpdir = new File(FOLDER);
844885
//if (!dir.exists()) { dir.mkdirs(); }
845-
File file = new File(dir, "aimsicd_dump.db");
886+
File file = new File(dumpdir, "aimsicd_dump.db");
887+
888+
//Bad coding:
889+
String aimdir = "/data/data/com.SecUpwN.AIMSICD/databases/";
890+
//Context.getFilesDir().getPath("com.SecUpwN.AIMSICD/databases"); ????
846891

847-
// We probably also need to test if we have the sqlite3 binary. (See Busbox checking code.)
892+
// We probably also need to test if we have the sqlite3 binary. (See Busybox checking code.)
848893
// Apparently pipes doesn't work from Java... (No idea why!?)
849894
//String execString = "/system/xbin/sqlite3 " + dir + "aimsicd.db '.dump' | gzip -c >" + file;
850-
String execString = "/system/xbin/sqlite3 " + dir + "aimsicd.db '.dump' >" + file;
895+
896+
// Both of these work, but "dump" makes an SQL file, whereas "backup" make a binary SQLite DB.
897+
//String execString = "/system/xbin/sqlite3 " + aimdir + "aimsicd.db '.dump' >" + file;
898+
String execString = "/system/xbin/sqlite3 " + aimdir + "aimsicd.db '.backup " +file + "'";
851899

852900
try {
853901
Log.i(TAG, "dumpDB() Attempting to dump DB to: " + file + "\nUsing: \"" + execString + "\"\n");
854-
// We may need SU here and cd...
855-
Process process = Runtime.getRuntime().exec(execString);
902+
// We need SU here and cd...
903+
CMDProcessor.runSuCommand(execString);
904+
//CMDProcessor.runSuCommand(execString).getStdout(); // Need import!
905+
//Process process = Runtime.getRuntime().exec(execString);
856906

857907
} catch (Exception e) {
858908
Log.e(TAG, "dumpDB() Failed to export DB dump file: " + e);
@@ -947,28 +997,39 @@ private void backup(String tableName) {
947997
* min_gps_precision (currently hard-coded)
948998
*
949999
* So there are really two steps in this procedure:
950-
* a) Remove false BTS from DBe_import
951-
* b) Mark unsafe BTSs in the DBe_import with "ref_cause" value.
1000+
* a) Remove bad BTSs from DBe_import
1001+
* b) Mark unsafe BTSs in the DBe_import with "rej_cause" value.
9521002
*
9531003
* See: #253 http://tinyurl.com/lybrfxb
9541004
* #203 http://tinyurl.com/mzgjdcz
9551005
*
9561006
* We filter:
9571007
*
1008+
* Used:
1009+
* RequestTask.java :: onPostExecute()
1010+
*
9581011
* Issues:
9591012
*
960-
* [ ] OPENCELLID_TABLE doesn't have a "Net" entry! WTF!
1013+
* [x] OPENCELLID_TABLE doesn't have a "Net" entry!
1014+
* [x] OPENCELLID_TABLE doesn't have a "Range" entry!
1015+
*
9611016
* [ ] Look into "long CID" and "Short CID" for UMTS/LTE...
9621017
* http://wiki.opencellid.org/wiki/FAQ
9631018
*
964-
* The formula for the long cell ID is as follows:
965-
* Long CID = 65536 * RNC + CID
1019+
* The formula for the long cell ID is as follows:
1020+
* Long CID = 65536 * RNC + CID
9661021
*
967-
* If you have the Long CID, you can get RNC and CID in the following way:
968-
* RNC = Long CID / 65536 (integer division)
969-
* CID = Long CID mod 65536 (modulo operation)
1022+
* If you have the Long CID, you can get RNC and CID in the following way:
1023+
* RNC = Long CID / 65536 (integer division)
1024+
* CID = Long CID mod 65536 (modulo operation)
9701025
*
1026+
* ChangeLog:
1027+
* 2015-01-29 E:V:A Added
9711028
*
1029+
* TODO: (1) Implement some kind of counter, to count how many cells was removed.
1030+
* TODO: (2) Better description of what was removed.
1031+
* TODO: (3) Give a return value for success/failure
1032+
* TODO: (4) Implement the "rej_cause" check and UPDATE table.
9721033
*/
9731034
//public void checkDBe( String tf_settings, int min_gps_precision ) {
9741035
public void checkDBe() {
@@ -977,29 +1038,63 @@ public void checkDBe() {
9771038
int min_gps_precision=50; // [m] Minimum acceptable GPS accuracy in meters.
9781039

9791040
String sqlq; // SQL Query string
1041+
1042+
//=============================================================
1043+
//=== DELETE bad cells from BTS data
1044+
//=============================================================
1045+
9801046
Log.d("checkDBe()", "Attempting to delete bad import data from DBe_import table...");
9811047

1048+
// =========== samples ===========
1049+
sqlq = "DELETE FROM " + OPENCELLID_TABLE + " WHERE Samples < 1";
1050+
mDb.rawQuery(sqlq, null);
1051+
1052+
// =========== range (DBe_import::avg_range) ===========
1053+
// TODO: OCID data marks many good BTS with a negative range so we can't use this yet.
1054+
//sqlq = "DELETE FROM " + OPENCELLID_TABLE + " WHERE Range < 1";
1055+
//mDb.rawQuery(sqlq, null);
1056+
9821057
// =========== LAC ===========
983-
sqlq = "DELETE FROM " + OPENCELLID_TABLE + " WHERE Lac <= 0";
1058+
sqlq = "DELETE FROM " + OPENCELLID_TABLE + " WHERE Lac < 1";
9841059
mDb.rawQuery(sqlq, null);
985-
// Delete cells with CDMA (4) LAC not in [1,65534]
986-
sqlq = "DELETE FROM " + OPENCELLID_TABLE + " WHERE Lac > 65534 AND Net=4";
1060+
1061+
// We should delete cells with CDMA (4) LAC not in [1,65534] but we can simplify this to:
1062+
// Delete ANY cells with a LAC not in [1,65534]
1063+
sqlq = "DELETE FROM " + OPENCELLID_TABLE + " WHERE Lac > 65534";
9871064
mDb.rawQuery(sqlq, null);
9881065
// Delete cells with GSM/UMTS/LTE (1/2/3/13 ??) (or all others?) LAC not in [1,65533]
989-
sqlq = "DELETE FROM " + OPENCELLID_TABLE + " WHERE Lac > 65533 AND Net!=4";
990-
mDb.rawQuery(sqlq, null);
1066+
//sqlq = "DELETE FROM " + OPENCELLID_TABLE + " WHERE Lac > 65533 AND Type!='CDMA'";
1067+
//mDb.rawQuery(sqlq, null);
9911068

9921069
// =========== CID ===========
993-
sqlq = "DELETE FROM " + OPENCELLID_TABLE + " WHERE CellID <= 0";
1070+
sqlq = "DELETE FROM " + OPENCELLID_TABLE + " WHERE CellID < 1";
9941071
mDb.rawQuery(sqlq, null);
995-
// Delete cells with UMTS/LTE (3,13) CID not in [1,268435455] (0xFFF FFFF)
996-
sqlq = "DELETE FROM " + OPENCELLID_TABLE + " WHERE CellID > 268435455 AND (Net=3 OR Net=13)";
1072+
1073+
// We should delete cells with UMTS/LTE (3,13) CID not in [1,268435455] (0xFFF FFFF) but
1074+
// we can simplify this to:
1075+
// Delete ANY cells with a CID not in [1,268435455]
1076+
sqlq = "DELETE FROM " + OPENCELLID_TABLE + " WHERE CellID > 268435455";
9971077
mDb.rawQuery(sqlq, null);
9981078
// Delete cells with GSM/CDMA (1-3,4) CID not in [1,65534]
999-
sqlq = "DELETE FROM " + OPENCELLID_TABLE + " WHERE CellID > 65534 AND (Net!=3 OR Net!=13)";
1000-
mDb.rawQuery(sqlq, null);
1079+
//sqlq = "DELETE FROM " + OPENCELLID_TABLE + " WHERE CellID > 65534 AND (Net!=3 OR Net!=13)";
1080+
//mDb.rawQuery(sqlq, null);
1081+
1082+
Log.i("checkDBe()", "Deleted BTS entries from DBe_import table with bad LAC/CID...");
1083+
1084+
//=============================================================
1085+
//=== UPDATE "rej_cause" in BTS data (DBe_import)
1086+
//=============================================================
1087+
1088+
// =========== isGPSexact ===========
1089+
// NOTE!! OCID present "changeable"=1 ==> isGPSexact (until we get new import!)
1090+
// UPADTE opencellid SET rej_cause = rej_cause + 3 WHERE isGPSexact=1;
1091+
1092+
// =========== avg_range ===========
1093+
// "UPDATE opencellid SET rej_cause = rej_cause + 3 WHERE avg_range < " + min_gps_precision;
1094+
1095+
// =========== time_first ===========
1096+
// "UPDATE opencellid SET rej_cause = rej_cause + 1 WHERE time_first < " + tf_settings;
10011097

1002-
Log.i("checkDBe()", "Deleted entries from DBe_import table with bad LAC/CID...");
10031098
}
10041099

10051100

@@ -1152,6 +1247,19 @@ public void onCreate(SQLiteDatabase database) {
11521247
* What: OpenCellID Cell Information Database
11531248
* Columns: _id,Lat,Lng,Mcc,Mnc,Lac,CellID,AvgSigStr,Samples,Timestamp
11541249
*
1250+
* Additional items (CSV):
1251+
* lat,lon,mcc,mnc,lac,cellid,averageSignalStrength,range,samples,changeable,radio,rnc,cid,psc,tac,pci,sid,nid,bid
1252+
* We need:
1253+
* lat,lon,mcc,mnc,lac,cellid,averageSignalStrength,range,samples,changeable,radio
1254+
*
1255+
* Dependencies:
1256+
* updateOpenCellID
1257+
* + "backup"
1258+
*
1259+
* ChengeLog:
1260+
* 2015-01-29 E:V:A Added: CSV: range, changeable, radio as:
1261+
* DBe: avg_range, isGPSexact, Type.
1262+
*
11551263
* TODO: (1) rename to TABLE_DBE_IMPORT ("DBe_import".)
11561264
* TODO: (2) add more items from CSV file to table.
11571265
*/
@@ -1165,8 +1273,14 @@ public void onCreate(SQLiteDatabase database) {
11651273
"Lac INTEGER, " +
11661274
"CellID INTEGER, " +
11671275
"AvgSigStr INTEGER, " +
1168-
"Samples INTEGER, " +
1169-
"Timestamp TIMESTAMP NOT NULL DEFAULT current_timestamp);";
1276+
"avg_range INTEGER, " + // new
1277+
"Samples INTEGER, " +
1278+
"isGPSexact INTEGER, " + // new
1279+
"Type TEXT, " + // new
1280+
// "rej_cause" // new
1281+
"Timestamp TIMESTAMP NOT NULL DEFAULT current_timestamp" +
1282+
//"Timestamp TIMESTAMP NOT NULL DEFAULT current_timestamp, " +
1283+
");";
11701284
database.execSQL(OPENCELLID_DATABASE_CREATE);
11711285

11721286
/**

‎app/src/main/java/com/SecUpwN/AIMSICD/utils/Helpers.java

+6
Original file line numberDiff line numberDiff line change
@@ -450,6 +450,12 @@ public static String getProp(String prop) {
450450
return CMDProcessor.runSuCommand("getprop " + prop).getStdout();
451451
}
452452

453+
public static String setProp(String prop, String value) {
454+
// We might wanna return the success of this. From mksh it is given by "$?" (0=ok, 1=fail)
455+
//return CMDProcessor.runSuCommand("setprop " + prop + " " + value);
456+
return CMDProcessor.runSuCommand("setprop " + prop + " " + value + "; echo \"$?\"").getStdout();
457+
}
458+
453459
public static String getSystemProp(Context context, String prop, String def) {
454460
String result = null;
455461
try {

‎app/src/main/java/com/SecUpwN/AIMSICD/utils/RequestTask.java

+25-2
Original file line numberDiff line numberDiff line change
@@ -245,6 +245,23 @@ protected void onProgressUpdate(Integer... values) {
245245
AIMSICD.mProgressBar.setProgress(values[0]);
246246
}
247247

248+
249+
/**
250+
* Description: This is where we:
251+
* 1) Check the success for OCID data download
252+
* 2) call the updateOpenCellID() to populate the DBe_import table
253+
* 3) call the checkDBe() to cleanup bad cells from imported data
254+
* 4) present a failure/success toast message
255+
* 5) set a system property to indicate that data has been downlaoded:
256+
* "setprop aimsicd.ocid_downloaded true"
257+
*
258+
* Issues:
259+
* [ ] checkDBe() is incomplete, due to missing RAT column in DBe_import
260+
*
261+
*
262+
* @param result
263+
*/
264+
// This is where we call the updateOPenCellID() to populate the DBe_import table
248265
@Override
249266
protected void onPostExecute(String result) {
250267
super.onPostExecute(result);
@@ -257,7 +274,10 @@ protected void onPostExecute(String result) {
257274
if (mDbAdapter.updateOpenCellID()) {
258275
Helpers.msgShort(mContext, "OpenCellID data successfully received");
259276
}
277+
278+
mDbAdapter.checkDBe();
260279
mDbAdapter.close();
280+
Helpers.setProp("aimsicd.ocid_downloaded", "true");
261281
} else {
262282
Helpers.msgLong(mContext, "Error retrieving OpenCellID data.\nCheck your network!");
263283
}
@@ -268,9 +288,11 @@ protected void onPostExecute(String result) {
268288
if (mDbAdapter.updateOpenCellID()) {
269289
Intent intent = new Intent(MapViewerOsmDroid.updateOpenCellIDMarkers);
270290
LocalBroadcastManager.getInstance(mContext).sendBroadcast(intent);
271-
Helpers.msgShort(mContext, "OpenCellID data successfully received and "
272-
+ "Map Markers updated");
291+
Helpers.msgShort(mContext, "OpenCellID data successfully received.\nMap Markers updated.");
292+
293+
mDbAdapter.checkDBe();
273294
mDbAdapter.close();
295+
Helpers.setProp("aimsicd.ocid_downloaded", "true");
274296
}
275297
} else {
276298
Helpers.msgLong(mContext, "Error retrieving OpenCellID data.\nCheck your network!");
@@ -306,6 +328,7 @@ protected void onPostExecute(String result) {
306328
} else {
307329
Helpers.msgLong(mContext, "Error backing up database");
308330
}
331+
//break;
309332
}
310333
}
311334
}

0 commit comments

Comments
 (0)
Please sign in to comment.