martedì 28 gennaio 2014

Problemi su bussola di smartphone

Alcune persone del Dipartimento di Scienze Geologiche dell'Universita' di Firenze mi hanno segnalato che la mia applicazione Geocompass non funziona. Il primo istinto e' stato dire: non e' possibile, l'applicazione e' stata scaricata da oltre 2500 persone non ho mai avuto segnalazioni in merito
Sono andato quindi a verificare di persona ed in effetti durante le prove il valore di Dip rimaneva fisso mentre il valore di Strike oscillava sensibilmente. Nelle mie prove non avevo osservato il fenomeno e sono rimasto perplesso. Una volta tornato a casa ho riprovato l'applicazione ed il difetto non si mostrava


A questo punto ho condotto la prova mostratta nel video. Con la stessa applicazione (la mia Geocompass), sullo stesso telefono (il mio Nexus S) ho fatto una prova di misura presso l'ufficio e dopo mezz'ora presso il DST ad Arcetri. Come si vede ad Arcetri le misure oscillano in un range di +- 20° (le misure sono state effettuate il piu' distante possibile da eventuali fonti di interferenza)

Si vede anche chiaramente che il sensore affetto e' il solo sensore magnetico infatti la misura di Dip e' eseguita solo tramite l'accelerometro (e' un calcolo in base alla scomposizione del vettore della forza di gravita') ed e' stabile mentre varia il valore di Strike e' che funzione sia dell'accelerometro sia della bussola digitale

Il sospetto e' che il sensore magnetico sia ingannato da qualche interferenza localizzata

ps: il fenomeno non sembra ascrivibile a cattiva calibrazione del sensore

giovedì 16 gennaio 2014

Arduino nano ed interruttore al mercurio

Un amico mi ha richiesto un sistema basato su Arduino che fosse alimentato da una batteria, che fosse il piu' piccolo possibile e che fosse sempre spento a meno di un evento (il rovesciamento della scheda)

La soluzione piuttosto stupida e' stata quella di usare come fonte di alimentazione una pila V4034PX della Varta da 6 V ed una Arduino micro (hanno piu' o meno le stesse dimensioni)

Tra il polo positivo della pila ed il Vcc dell'Arduino e' stato messo un interruttore a Mercurio (che normalmente e' in posizione aperta). Quando la scheda viene rovesciata il circuito si chiude e si accende l'Arduino


sdf




martedì 14 gennaio 2014

Da Os X 10.6 a 10.7 via USB - Errore su installazione

Mi sono trovato a dover aggiornare un MacBook (Intel Core Due Duo con 2 Giga di Ram) per il passaggio da Mac Os X 10.6 a 10.7. (fra parentesi ho pochissima esperienza con i Mac ed in particolari con la nuova generazione Intel)
Non avendo un supporto fisico (leggasi DVD) ho preparato una chiavetta USB con il metodo che ho riassunto nel video sottostante. In sintesi si prende una chiavetta da almeno 8 Giga, si apre Utility Disco, si formatta la chiavetta e poi si ripristina sulla stessa chiavetta il .dmg del sistema operativo



A questo punto ho fatto partire la macchina tenendo premuto il tasto Option (Alt) e selezionando la chiavetta come disco di avvio. In tutte le prove effettuate, dopo un po' di pensatoio da parte dell'installer, viene sempre generato questo errore. Ho provato a rimuovere la partizione bootcamp, provato a formattare tutto il disco ... niente da fare



Frugando per forum ho trovato l'indicazione di formattare la PRAM prima di tentare l'installazione. A questo punto ho proceduto accendendo il calcolatore e premendo subito la combinazione Option+Command+P+R, il Mac fa Boing e poi fa il reboot. A questo punto ho fatto ripartire l'installazione da Usb Key e tutto e' terminato in modo corretto


Compressione SMS in Android (2)

Riprendendo dalla puntata precedente, in questo caso la compressione non e' orientata ai caratteri ma si basa sull'ottimizzare il numero di bit per comprimere il dato. Come gia' detto l'obbiettivo e' trasferire informazioni geografiche quindi coordinate lat/long che possono essere descritte come numeri in virgola mobile (non e' previsto avere segni di separazione perche' sara' solo la posizione a determinare la distinzione tra un dato ed il successivo)

Una coordinata in gradi decimali (se non ho sbagliato) necessita' di almeno 5 decimali per avere una precisione al secondo di arco in grado sessagesimali.
La logica e' piu' o meno questa:
1) si prende il numero in virgola mobile e lo si converte nella sua rappresentazione binaria (come stringa)
2) si divide la stringa in pezzi da 7 bit (per il formato SMS)
3) si prendono solo i primi 5 gruppi di 7 bit (il resto dell'informazione e' ridondante)
4) i 7 bit vengono convertiti in un intero (0-127) e quindi nel corrispondente caratttere della tabella SMS
5) il percorso inverso per la riconversione in float

il vantaggio non e' drammatico. Si descrive un numero che puo' essere scritto con 8 caratteri in 5 gruppi da 7 bit (quindi il messaggio occupa circa 0.62 dell'originale, ovvero 1.6 dipende da punto si vede)
Questi sono i passaggi

-------------------------------------------------------------------
Messaggio originale :43.26432
100000001000101101000011101010100111100110111011101011011100000
Messaggio compresso : ¡"h:S
100000001000101101000011101010100110000000000000000000000000000
Messaggio decompresso : 43.26431846618652
-------------------------------------------------------------------
ed ecco il codice

--------------------------------------------------------------

package sms_compr;

import java.math.BigInteger;

/**
 *
 * @author l.innocenti
 */
public class Sms_compr {
    private static int valore;
    private static String reverse = "";
    private static String passaggio = "";
    
    

     static private int converti_sms(char carattere)
    {
       int codice=0;
       switch (carattere)
            {
             case '@': codice=0;break;
             case '£': codice=1;break;
             case '$': codice=2;break;
             case '¥': codice=3;break;
             case 'è': codice=4;break;
             case 'é': codice=5;break;
             case 'ù': codice=6;break;
             case 'ì': codice=7;break;
             case 'ò': codice=8;break;
             case 'Ç': codice=9;break;
             case '\n': codice=10;break;
             case 'Ø': codice=11;break;
             case 'ø': codice=12;break;
             case '\r': codice=13;break;
             case 'Å': codice=14;break;
             case 'å': codice=15;break;
             case 'Δ': codice=16;break;
             case '_': codice=17;break;
             case 'Φ': codice=18;break;
             case 'Γ': codice=19;break;
             case 'Λ': codice=20;break;
             case 'Ω': codice=21;break;
             case 'Π': codice=22;break;
             case 'Ψ': codice=23;break;
             case 'Σ': codice=24;break;
             case 'Θ': codice=25;break;
             case 'Ξ': codice=26;break;
             //case '': codice=27;break;
             case 'Æ': codice=28;break;
             case 'æ': codice=29;break;
             case 'ß': codice=30;break;
             case 'É': codice=31;break;
             case ' ': codice=32;break;
             case '!': codice=33;break;
             case '"': codice=34;break;
             case '#': codice=35;break;
             case '¤': codice=36;break;
             case '%': codice=37;break;
             case '&': codice=38;break;
             case '\'': codice=39;break;
             case '(': codice=40;break;
             case ')': codice=41;break;
             case '*': codice=42;break;
             case '+': codice=43;break;
             case ',': codice=44;break;
             case '-': codice=45;break;
             case '.': codice=46;break;
             case '/': codice=47;break;
             case '0': codice=48;break;
             case '1': codice=49;break;
             case '2': codice=50;break;
             case '3': codice=51;break;
             case '4': codice=52;break;
             case '5': codice=53;break;
             case '6': codice=54;break;
             case '7': codice=55;break;
             case '8': codice=56;break;
             case '9': codice=57;break;
             case ':': codice=58;break;
             case ';': codice=59;break;
             case '<': codice=60;break;
             case '=': codice=61;break;
             case '>': codice=62;break;
             case '?': codice=63;break;
             case '¡': codice=64;break;
             case 'A': codice=65;break;
             case 'B': codice=66;break;
             case 'C': codice=67;break;
             case 'D': codice=68;break;
             case 'E': codice=69;break;
             case 'F': codice=70;break;
             case 'G': codice=71;break;
             case 'H': codice=72;break;
             case 'I': codice=73;break;
             case 'J': codice=74;break;
             case 'K': codice=75;break;
             case 'L': codice=76;break;
             case 'M': codice=77;break;
             case 'N': codice=78;break;
             case 'O': codice=79;break;
             case 'P': codice=80;break;
             case 'Q': codice=81;break;
             case 'R': codice=82;break;
             case 'S': codice=83;break;
             case 'T': codice=84;break;
             case 'U': codice=85;break;
             case 'V': codice=86;break;
             case 'W': codice=87;break;
             case 'X': codice=88;break;
             case 'Y': codice=89;break;
             case 'Z': codice=90;break;
             case 'Ä': codice=91;break;
             case 'Ö': codice=92;break;
             case 'Ñ': codice=93;break;
             case 'Ü': codice=94;break;
             case '§': codice=95;break;
             case '¿': codice=96;break;
             case 'a': codice=97;break;
             case 'b': codice=98;break;
             case 'c': codice=99;break;
             case 'd': codice=100;break;
             case 'e': codice=101;break;
             case 'f': codice=102;break;
             case 'g': codice=103;break;
             case 'h': codice=104;break;
             case 'i': codice=105;break;
             case 'j': codice=106;break;
             case 'k': codice=107;break;
             case 'l': codice=108;break;
             case 'm': codice=109;break;
             case 'n': codice=110;break;
             case 'o': codice=111;break;
             case 'p': codice=112;break;
             case 'q': codice=113;break;
             case 'r': codice=114;break;
             case 's': codice=115;break;
             case 't': codice=116;break;
             case 'u': codice=117;break;
             case 'v': codice=118;break;
             case 'w': codice=119;break;
             case 'x': codice=120;break;
             case 'y': codice=121;break;
             case 'z': codice=122;break;
             case 'ä': codice=123;break;
             case 'ö': codice=124;break;
             case 'ñ': codice=125;break;
             case 'ü': codice=126;break;
             case 'à': codice=127;break;
       }
       return codice;
    }

    public static void main(String[] args) {
         char[] sms = new char[128];
        

        sms[0] = '@';
        sms[1] = '£';
        sms[2] = '$';
        sms[3] = '¥';
        sms[4] = 'è';
        sms[5] = 'é';
        sms[6] = 'ù';
        sms[7] = 'ì';
        sms[8] = 'ò';
        sms[9] = 'Ç';
        sms[10] = '\n';
        sms[11] = 'Ø';
        sms[12] = 'ø';
        sms[13] = '\r';
        sms[14] = 'Å';
        sms[15] = 'å';
        sms[16] = 'Δ';
        sms[17] = '_';
        sms[18] = 'Φ';
        sms[19] = 'Γ';
        sms[20] = 'Λ';
        sms[21] = 'Ω';
        sms[22] = 'Π';
        sms[23] = 'Ψ';
        sms[24] = 'Σ';
        sms[25] = 'Θ';
        sms[26] = 'Ξ';
        //sms[27] = '';
        sms[28] = 'Æ';
        sms[29] = 'æ';
        sms[30] = 'ß';
        sms[31] = 'É';
        sms[32] = ' ';
        sms[33] = '!';
        sms[34] = '"';
        sms[35] = '#';
        sms[36] = '¤';
        sms[37] = '%';
        sms[38] = '&';
        sms[39] = '\'';
        sms[40] = '(';
        sms[41] = ')';
        sms[42] = '*';
        sms[43] = '+';
        sms[44] = ',';
        sms[45] = '-';
        sms[46] = '.';
        sms[47] = '/';
        sms[48] = '0';
        sms[49] = '1';
        sms[50] = '2';
        sms[51] = '3';
        sms[52] = '4';
        sms[53] = '5';
        sms[54] = '6';
        sms[55] = '7';
        sms[56] = '8';
        sms[57] = '9';
        sms[58] = ':';
        sms[59] = ';';
        sms[60] = '<';
        sms[61] = '=';
        sms[62] = '>';
        sms[63] = '?';
        sms[64] = '¡';
        sms[65] = 'A';
        sms[66] = 'B';
        sms[67] = 'C';
        sms[68] = 'D';
        sms[69] = 'E';
        sms[70] = 'F';
        sms[71] = 'G';
        sms[72] = 'H';
        sms[73] = 'I';
        sms[74] = 'J';
        sms[75] = 'K';
        sms[76] = 'L';
        sms[77] = 'M';
        sms[78] = 'N';
        sms[79] = 'O';
        sms[80] = 'P';
        sms[81] = 'Q';
        sms[82] = 'R';
        sms[83] = 'S';
        sms[84] = 'T';
        sms[85] = 'U';
        sms[86] = 'V';
        sms[87] = 'W';
        sms[88] = 'X';
        sms[89] = 'Y';
        sms[90] = 'Z';
        sms[91] = 'Ä';
        sms[92] = 'Ö';
        sms[93] = 'Ñ';
        sms[94] = 'Ü';
        sms[95] = '§';
        sms[96] = '¿';
        sms[97] = 'a';
        sms[98] = 'b';
        sms[99] = 'c';
        sms[100] = 'd';
        sms[101] = 'e';
        sms[102] = 'f';
        sms[103] = 'g';
        sms[104] = 'h';
        sms[105] = 'i';
        sms[106] = 'j';
        sms[107] = 'k';
        sms[108] = 'l';
        sms[109] = 'm';
        sms[110] = 'n';
        sms[111] = 'o';
        sms[112] = 'p';
        sms[113] = 'q';
        sms[114] = 'r';
        sms[115] = 's';
        sms[116] = 't';
        sms[117] = 'u';
        sms[118] = 'v';
        sms[119] = 'w';
        sms[120] = 'x';
        sms[121] = 'y';
        sms[122] = 'z';
        sms[123] = 'ä';
        sms[124] = 'ö';
        sms[125] = 'ñ';
        sms[126] = 'ü';
        sms[127] = 'à';
        double lat = 43.26432; //64 bit
        String stringa;
        String compressa = "";
        
        System.out.println("Messaggio originale :"+ lat);

        //convert il double in una stringa con la conversione binaria del dato
        stringa = Long.toBinaryString(Double.doubleToRawLongBits(lat));
        System.out.println(stringa);
        
        //divide il dato in pezzi da 7 bit
        //per mandare il dato via SMS con la tabella caratteri SMS
        String b1 = stringa.substring(0, 7);
        String b2 = stringa.substring(7, 14);
        String b3 = stringa.substring(14, 21);
        String b4 = stringa.substring(21, 28);
        String b5 = stringa.substring(28, 35);
        //String b6 = stringa.substring(35, 42);
        //String b7 = stringa.substring(42, 49);
        //String b8 = stringa.substring(49, 56);
      
        //convert il valore binario a base 7 in intero
        int d1 = Integer.parseInt(b1, 2);
        int d2 = Integer.parseInt(b2, 2);
        int d3 = Integer.parseInt(b3, 2);
        int d4 = Integer.parseInt(b4, 2);
        int d5 = Integer.parseInt(b5, 2);
        //int d6 = Integer.parseInt(b6, 2);
        //int d7 = Integer.parseInt(b7, 2);
        //int d8 = Integer.parseInt(b8, 2);
        
        //usando la tabella di compressione prende i primi 5 gruppi di 7 bit
        //e li codifica come SMS
        //compressa = compressa + sms[d1]+sms[d2]+sms[d3]+sms[d4]+sms[d5]+sms[d6]+sms[d7]+sms[d8];
        compressa = compressa + sms[d1]+sms[d2]+sms[d3]+sms[d4]+sms[d5];
        System.out.println("Messaggio compresso : "+compressa);
        
        for (int t=0; t<compressa.length();t++)
            {
            valore = converti_sms(compressa.charAt(t));
            String v = Integer.toBinaryString(valore);
           reverse = new StringBuffer(v).toString();
           //System.out.println(reverse);


        

            while ((reverse.length() %7) != 0)
                {
                reverse = "0"+reverse ;
                }
            passaggio = passaggio + reverse;
            //System.out.println("a "+reverse);

            }
        

        
        passaggio = passaggio + "0000000000000000000000000000";
        System.out.println(passaggio);

        
        double doubleVal = Double.longBitsToDouble(new BigInteger(passaggio, 2).longValue());
        System.out.println("Messaggio decompresso : "+doubleVal);
        
        
        
    }
    
}

Compressione SMS in Android

Per la solita applicazione su cui sto lavorando adesso, sarebbe utile effettuare la compressione dei dati di un SMS per trasportare la maggiore quantita' di informazioni. Ho fatto un paio di prove, la prima e' questa basata semplicemente sulla compressione dei caratteri

Fonte Wikipedia


I dati previsti sono numerici con alcuni segni di interpunzione per cui l'intero set di caratteri puo' essere descritto con un set di 16 caratteri (4 bit). I dati trasportati sono coordinate geografiche, informazioni sul tempo, dati di antenne e stato della batteria
Considerando che la tavola dei caratteri piu' semplice per gli SMS racchiude 7 bit c'e' un discreto guadagno (un fattore di 1.75)

Attualmente gli SMS permettono di inviare 1120 bit, ovvero 160 caratteri con la tabella a 7 bit e 140 con la tabella ad 8 bit.(le tabelle dei codici SMS non sono confrontabili con quelle ASCII)

Usando il codice riportato dopo il salto e' stata effettuata una prova codificando

---------------------------------------------
Messaggio : 12.3455;43.123123;22;-45;13:23:21 12/03/2013
Lungh. messaggio 44
Valore numerici convertiti a 7 bit 72 22 11 85 39 120 34 98 72 120 17 58 45 116 33 30 68 7 97 71 84 0 23 2 72 127 127 
Messaggio compresso a 7 Bit tabella GSM : HΠØU'x"bHx_:-t!ßDìaGT@Ψ$Hàà
Lungh.Mess.Compresso 27
Messaggio Decompresso :12.3455;43.123123;22;-45;13:23:21 12/03/2013   
---------------------------------------------

Come si osserva che il messaggio e' compresso con un fatto di circa 1.7 (il limite teorico di 1.75 non e' raggiunto per una serie di aggiustamenti nel passare da 4 a 7 bit)


Smartphone e privacy

Ieri ho trovato questo BlackBerry a terra per strada. E' il secondo cellulare che trovo, il primo lo trovai al cinema oltre 10 anni fa (considerando la diffusione dei cellulari direi che la mia media di ritrovamento e' piuttosto scarsa)


Il cellulare era acceso e sbloccato per cui nel giro di 5 minuti ho trovato nell'agenda un numero relativo ad un familiare del proprietario ed il telefono e' stato restituito
C'e' pero' da fare una considerazione: se fossi stato un male intenzionato mi sono trovato per le mani un oggetto con configurato un account Google (con sicuramente l'account di posta configurato viste le icone sulla home) ma anche un account Facebook (sempre viste le icone sulla home) e con un po' di fortuna avrei raccattato una quantita' di dati sensibili preoccupante (se l'utente usava anche GDrive ero a cavallo)
Dieci anni fa ritrovare un telefono voleva dire, se maleintenzionati, farsi qualche telefonata gratuita e magari tenersi il telefono, oggi il rischio della perdita di uno smartphone e' decisamente preoccupante.
Di fatto lo stesso motivo che mi ha permesso di riconsegnare in breve tempo il telefono (ovvero il fatto che non fosse protetto con un pin code o simili) potrebbe riverlarsi, nelle mani sbagliate, un grave rischio per il conto in banca del proprietario

Debugger integrato ESP32S3

Aggiornamento In realta' il Jtag USB funziona anche sui moduli cinesi Il problema risiede  nell'ID USB della porta Jtag. Nel modulo...