venerdì 12 dicembre 2025

Hacking Lisciani Step Imparotutto

 

Per smontare il gioco si deve togliere la plastica antiscivolo al di sotto del gioco. Le viti sono nascoste li' ed usando le dita non si riescono ad individuare i fori 

Una volta rimossa la parte superiore devono rimuovere i cavi del pulsante superiore, il cavo dello speaker ed il lettore delle carte. I cavi hanno una connessione fast e si smontando semplicemente

 

si accede quindi alla scheda madre. Al centro si osserva un microcontrollore FCM32F030C8T6, si sono due shift register 74HC959 ed i controller per i motori passo passo ULN2003C 

Nella scheda madre e' inserita una SD Card rimuovibile (fermata solo da nastro adesivo trasparente) da 512 Mb formattata Fat32 ed occupata per circa 130 Mb. Immagino che questo sistema permetta di configurare facilmente il dispositivo per diversi mercati con differenti linguaggi

Il contenuto e' costuito in folder (nel mio caso numerati da 005 a 126 piu' una BACK)

In ogni folder ci sono i file wav del gioco. Per esempio nel folder 005 ci sono file wav numerati da 31.wav a 35.wav per la carta Leone. I file wav sono codificato mono 16 bit signed integer PCM, 352 kps, sample 22.05 KHz con campo commento iTunPGAP 0

Inoltre sono presenti uno o piu' file .txt (step.txt stepn.txt e ans.txt, ) con il seguente contenuto


!0#0,0,0,0#635,1782;630,1785;624,1788;619,1791;614,1795;609,1798;604,1801;598,1805;593,1808;588,1812;582,1815;577,1819;571,1823;566,1826;560,1830;555,1834;549,1838;543,1842;538,1846;532,1850;526,1855;526,1855;528,1859;529,1863;531,1868;533,1872;534,1877;536,1881;537,1885;539,1890;540,1895;542,1899;543,1904;544,1908;546,1913;547,1917;548,1922;549,1927;551,1931;552,1936;553,1941;554,1946;555,1950;555,1950;561,1946;567,1942;574,1938;580,1934;586,1930;592,1926;598,1923;604,1919;610,1915;616,1912;622,1908;628,1905;633,1901;639,1898;645,1895;650,1892;656,1889;662,1886;667,1883;673,1880;673,1880;671,1875;670,1870;668,1865;667,1860;665,1856;663,1851;662,1846;660,1842;658,1837;657,1832;655,1828;653,1823;651,1818;649,1814;647,1809;645,1804;643,1800;641,1795;639,1791;637,1786;635,1782;
!1#0,0,0,0#663,1850;668,1848;673,1845;678,1843;683,1841;688,1839;692,1837;697,1835;702,1832;707,1830;707,1830;712,1827;718,1825;723,1822;728,1819;733,1816;737,1813;742,1811;747,1808;752,1805;756,1802;761,1799;765,1796;769,1793;773,1789;778,1786;782,1783;786,1780;790,1776;793,1773;797,1770;801,1766;804,1763;808,1759;811,1755;814,1752;817,1748;820,1744;823,1740;826,1736;829,1732;832,1728;834,1724;837,1720;839,1716;841,1712;843,1708;845,1703;847,1699;849,1695;851,1690;852,1686;853,1681;855,1676;856,1672;857,1667;858,1662;859,1657;859,1652;860,1647;860,1642;860,1637;860,1632;860,1626;860,1621;860,1616;859,1610;859,1605;858,1599;857,1594;856,1588;855,1582;853,1577;852,1571;850,1565;848,1559;846,1553;844,1547;842,1541;839,1535;836,1529;833,1523;831,1517;827,1510;824,1504;821,1498;817,1491;813,1485;809,1479;805,1472;801,1466;796,1460;792,1453;787,1447;782,1441;777,1434;772,1428;767,1422;761,1416;756,1409;756,1409;750,1403;745,1397;739,1391;733,1385;727,1380;721,1374;715,1368;709,1363;703,1358;697,1353;690,1348;684,1343;678,1338;672,1334;666,1329;659,1325;653,1321;647,1317;641,1313;634,1309;628,1305;622,1302;616,1299;610,1296;604,1293;598,1290;592,1287;586,1285;580,1283;574,1280;568,1278;562,1276;556,1275;550,1273;545,1272;539,1271;533,1270;528,1269;522,1268;517,1267;511,1267;506,1266;501,1266;496,1266;490,1266;485,1266;480,1267;475,1267;470,1268;465,1268;461,1269;456,1270;451,1272;447,1273;442,1274;437,1276;433,1277;428,1279;424,1281;420,1283;416,1285;411,1287;407,1290;403,1292;399,1295;395,1297;391,1300;387,1303;383,1306;380,1309;376,1312;372,1316;369,1319;365,1323;361,1326;358,1330;354,1334;351,1337;348,1341;344,1345;341,1350;338,1354;335,1358;332,1363;328,1367;325,1372;322,1376;319,1381;316,1386;316,1386;314,1390;311,1395;309,1400;306,1404;304,1409;301,1413;299,1418;297,1423;295,1427;292,1432;
!1#0,0,0,0#325,1519;328,1514;331,1509;334,1504;336,1499;337,1493;339,1488;339,1483;339,1477;339,1472;337,1467;336,1462;334,1457;331,1453;328,1449;325,1445;321,1442;317,1439;312,1437;307,1435;302,1433;297,1433;292,1432;287,1432;281,1433;276,1434;270,1436;265,1438;260,1441;254,1444;250,1448;245,1452;241,1456;236,1461;233,1466;229,1471;226,1477;223,1482;221,1488;219,1494;218,1499;217,1505;217,1510;217,1516;217,1521;218,1526;220,1530;222,1534;224,1538;227,1542;230,1545;234,1547;238,1550;243,1551;247,1552;253,1553;258,1553;263,1553;269,1553;275,1551;280,1550;286,1548;292,1545;297,1542;303,1539;308,1535;313,1532;317,1527;322,1523;325,1519;
 

 sono presenti anche dei file di lunghezza nulla. Il nome del file e' descrittivo del contenuto della cartella. turtle.txt di lunghezza zero indica che i file .wav e step.txt sono relativi alla carta della tartaruga 

in pratica queste le istruzioni per muovere il pennino. Si tratta di coppie di valori interi separati da virgola e le varie coppie sono divise da punti e virgola

Se si plottano le coppie di valori della carta Leone si ha questo risultato

questo invece il tracciato per la barca

Questo e' il programma per visualizzare il file step.txt come un disegno


import matplotlib.pyplot as plt
import os

def parse_scribbles(data_string):
    """
    Parsa la stringa di dati nel formato '!<tipo>#0,0,0,0#x1,y1;x2,y2;...'
    e restituisce una lista di dizionari, ognuno contenente il tipo e le coordinate.
    """
    scribbles = []
    # Rimuovi spazi e dividi i blocchi principali per '!'
    blocks = data_string.strip().split('!')
   
    for block in blocks:
        if not block.strip():
            continue
           
        # Tenta di dividere il blocco in [tipo], [info non usate], [coordinate]
        parts = block.split('#')
        if len(parts) < 3:
            continue
       
        try:
            # Il tipo è il primo carattere del blocco (e.g., '0' o '1')
            scribble_type = int(parts[0].strip())
            coords_string = parts[2]
        except ValueError:
            # Salta se il tipo non è un numero valido
            continue

        # Dividi la stringa delle coordinate per ';' per ottenere i singoli punti
        points_str = coords_string.split(';')
       
        x_coords = []
        y_coords = []
        for point_str in points_str:
            if not point_str.strip():
                continue
            try:
                # Dividi x e y per ','
                x, y = map(int, point_str.split(','))
                x_coords.append(x)
                y_coords.append(y)
            except ValueError:
                # Salta se un punto non è nel formato 'x,y' valido
                continue

        if x_coords and y_coords:
            scribbles.append({'type': scribble_type, 'x': x_coords, 'y': y_coords})
           
    return scribbles

def plot_scribbles(scribbles):
    """
    Genera il plot dei dati delle linee.
    """
    plt.figure(figsize=(10, 8))

    # Definisci colori e etichette per i diversi tipi di tratto
    colors = {0: 'blue', 1: 'red', 2: 'green', 3: 'purple'} # Puoi espandere i tipi
    labels = {0: 'Tipo 0 (Penna)', 1: 'Tipo 1 (Marcatore)', 2: 'Tipo 2', 3: 'Tipo 3'}

    plotted_types = set()
    for scribble in scribbles:
        scribble_type = scribble['type']
       
        # Scegli colore e etichetta, assicurandoti che l'etichetta appaia solo una volta
        color = colors.get(scribble_type, 'gray')
        label_to_use = labels.get(scribble_type, f'Tipo {scribble_type}') if scribble_type not in plotted_types else None
       
        # Plotta la linea
        plt.plot(scribble['x'], scribble['y'],
                 color=color,
                 marker=None, # Non mostrare i singoli punti per non appesantire il plot
                 linestyle='-',
                 linewidth=2,
                 label=label_to_use)
       
        plotted_types.add(scribble_type)

    # Inverti l'asse Y perché le coordinate delle immagini spesso hanno Y=0 in alto
    plt.gca().invert_yaxis()
   
    # Imposta un rapporto di aspetto uguale per evitare distorsioni (disegno non stirato)
    plt.gca().set_aspect('equal', adjustable='box')

    # Aggiungi titoli e legenda
    plt.title('Visualizzazione Disegno da File TXT')
    plt.xlabel('Coordinata X')
    plt.ylabel('Coordinata Y')
   
    if plotted_types:
        plt.legend(loc='best')
       
    plt.grid(True, linestyle='--', alpha=0.6)
    plt.show()

# --- Esecuzione Principale ---
file_name = 'step.txt'

# 2. Leggi il file di input
try:
    with open(file_name, 'r') as f:
        file_content = f.read()
except FileNotFoundError:
    print(f"Errore: File '{file_name}' non trovato.")
    exit()

# 3. Parsa e Plotta
if file_content.strip():
    parsed_scribbles = parse_scribbles(file_content)
    if parsed_scribbles:
        plot_scribbles(parsed_scribbles)
    else:
        print("Nessun dato di disegno valido trovato nel file.")
else:
    print("Il file è vuoto.")


 


 


questo e' il pulsante superiore


 questa e' la scheda del lettore delle carte. Si tratta di un lettore ottico con 7 coppie di emettitore/ricevitore .. in linea di principio sono 7 bit quindi in linea di principio sarebbero possibili 128 carte distinte.. il sistema pero' e' simmetrico e non so come vengono gestite le carte messe al contrario


 se i mettono le carte controluce si osserva alcune zone opache per la lettura della carte ..le carte non sono simmetriche quindi dovrebbe essere confermato il numero di 128 distinte carte possibili

Facendo un po' di prove ho trovato la regola. Se la carta fa passare luce vale come Bit=1, altrimenti settato Bit=0

La posizione e' la seguente. in pratica i bit si leggono in senso orario partendo da quello piu' significativo in alto a destra

Bit0   Bit6 

Bit1   Bit5

Bit2   Bit4

        Bit3 

Per esempio la carta la lettera P ha la seguente disposizione

1 0
1 1
0 0
 1

ricostruendo la sequenza si ottiene 101011 che equivale al numero decimale 43. Se sulla scheda SD si va al folder 43 troveremo gli audio appunto della lettera P

Altro esempio con la carta Arancia

0 0
1 0
1 1
 0
la sequenza diventa 10110 ovvero decimale 22  

 

 

i motori stepper sono dei TH24BYJ

l'integrato per la ricarica della batteria e' un ETA9742

connessione per il modulo di ricarica USB-C. La porta USB funziona quindi solo come alimentazione. Sulla scheda madre si sono pero' dei reofori vicino alla scritta HHQUICK_V2.3 che portano direttamente al microntrollore e potrebbe essere la porta di programmazione

ed a questo punto perche' non farlo parlare toscano


 

 

 

 

 

 

 

 

 

Nessun commento:

Posta un commento

Chiavetta ALIA

Sono maledettamente distratto e stavo cercando di vedere se riesco a replicare la chiavetta dei cassonetti di Firenze senza dover per forza ...