Autor Tema: Bootloader  (Leído 3459 veces)

0 Usuarios y 1 Visitante están viendo este tema.

Desconectado elreypic2

  • Colaborador
  • PIC24H
  • *****
  • Mensajes: 1297
Re:Bootloader
« Respuesta #15 en: 14 de Septiembre de 2017, 16:25:15 »
Que tal remi04,

Definitivamente tu idea es viable. No tengo experiencia usando el bootloader de CCS pero con paciencia y dedicación tu modificación sería posible.
En cuanto a lo del tinybootloader no he tratado de ensamblarlo usando MPLABX, lo había intentado satisfactoriamente en las verisiones anteriores del MPLAB. Hoy por la noche lo intento y te comento cual fue el resultado. Yo tengo la versión del MPLABX 3.6 si mal no recuerdo.

En mi opinión creo que tinybootloader es la mejor opción porque el código ya esta listo para grabar los valores de la eeprom como los necesitas. Si el problema es la compilación eso tiene solución. Como te lo comenté voy a intentar ensamblar un bootloader ejemplo (hoy por la noche que llegue a casa) y te comento los resultados.

Saludos,

elreypic.

Desconectado planeta9999

  • Moderadores
  • DsPIC30
  • *****
  • Mensajes: 3520
    • Pinballsp
Re:Bootloader
« Respuesta #16 en: 14 de Septiembre de 2017, 21:44:44 »

Aqui tienes un bootloader encriptado, en C, para Pic18. Para encriptar usa Xtea.

http://www.microchip.com/forums/m/tm.aspx?m=126770&mpage=2&key=&&p=#292501

Desconectado elreypic2

  • Colaborador
  • PIC24H
  • *****
  • Mensajes: 1297
Re:Bootloader
« Respuesta #17 en: 14 de Septiembre de 2017, 22:20:16 »
Pues lo prometido es deuda.

He tomado uno de los archivos fuentes (en ensamblador) para el tinybootloader y ensamblarlo usando MPLABX V3.6 y los resultados son satisfactorios. No he tenido problema alguno en generar el archivo hex. Aquí una snapshot:


* MPLABX_test.JPG
(163.37 kB, 1347x672 - visto 283 veces)


remi04, definitivamente algo estas haciendo mal y por eso no puedes ensamblar el codigo fuente y generar el hexadecimal.

elreypic.
« Última modificación: 14 de Septiembre de 2017, 22:22:22 por elreypic2 »

Desconectado remi04

  • PIC24F
  • *****
  • Mensajes: 657
Re:Bootloader
« Respuesta #18 en: 18 de Septiembre de 2017, 17:44:37 »
Gracias a todos. La verdad es que estoy aprendiendo muchas cositas nuevas y entre toda la info que me habeis puesto, estudiando los ficheros estoy poco a poco desarrollando mi propio bootloader.  Tambien he acabado instalando eclipse con mingw para poder compilar los encriptadores y de paso, aprender mas.

Un saludo.

Desconectado remi04

  • PIC24F
  • *****
  • Mensajes: 657
Re:Bootloader
« Respuesta #19 en: 24 de Septiembre de 2017, 13:15:05 »
Al final, entre toda la ayuda facilitada y comiendome la cabeza he conseguido elaborar mi propio bootloader con xtea , que aunque no es liviano precisamente cumple para lo que necesito y al ser para propio uso y cargar una aplicación en concreto pues me vale aunque no sea lo más optimo.

  Comparto el codigo con todos por si alguien le puede sacar provecho o para leer sugerencias de como corregir o hacer de otras formas algunos disparates del codigo.  :D :D

 Para encriptar encontré una aplicacion en C++ que se puede compilar con eclipse usando un minigw. También pongo este codigo mas abajo. 

  Un saludo.

Código: C
  1. // erase_size = 64
  2. // write_size = 32
  3. // program_memory = 65536
  4. // Bootloader con XTEA elaborado a partir de ejemplos y otras implementaciones.
  5.  
  6.  
  7. #include<18f26k20.h>
  8. #fuses INTRC_IO, NOWDT, BROWNOUT, PUT, NOLVP, NOMCLR, PBADEN,
  9. #use delay(clock=64000000)
  10. #use rs232(baud=115200, xmit=PIN_C6, rcv=PIN_C7,STREAM=TX)                          // Comunicación con el cargador (Coolterm, realterm, etc).
  11. #use rs232(baud=9600,parity=N,xmit=PIN_C7,rcv=PIN_C6,bits=8,FORCE_SW,STREAM=LCD)    // Comunicacion rs232 con la pantalla lcd ascii.
  12. #define PUSH_BUTTON PIN_B4                                                         // pulsador de modo bootloader
  13. #byte OSCCON=getenv("SFR:OSCCON")                                                  // registo de configuración del oscilador.
  14. #bit PLLEN=getenv("BIT:PLLEN")                                                     // registo de configuración del oscilador. PLL
  15. #byte OSCTUNE=getenv("SFR:OSCTUNE")                                                // registo de configuración del oscilador.
  16. #define CLK_16 0x70                                                                 // configuración para oscilador a 16 Mhz.                  
  17. #BIT CREN = 0xfab.4                                                                // control recepción modulo usart
  18.  
  19.  
  20. #define XON    0x11                             // control de flujo datos desde el cargador por sotware
  21. #define XOFF   0x13                             // control de flujo datos desde el cargador por sotware
  22.  
  23. #org 0xc84,0xfffe {}              // a partir de la posicion 0xc80 hasta el final de la flash es para el programa a cargar
  24.                                   // pero permitimos a bootloader escribir hasta 0xc84 para que sobreescriba la función del vector de arranque.
  25.  
  26.  
  27.  
  28. int8  checksum, line_type;                                  //  Control de checksum y almacen del tipo de linea hex respectivamente.
  29. int16 l_addr,h_addr=0;
  30. int32 addr;                                                 // almacena el addres donde hay que cargar el buffer data en la flash
  31. int8  dataidx, i, count;                                  // indice buffer de data, i = control usos multiples, count = almacena numero de bytes de una linea relevante hex.
  32. int8  data[32];                                            // buffer de datos enteros de 8 bits ya convertidos listos para enviar a la flash,
  33. int16 key [4] = {0xface,0xdead,0xbabe,0xd00d};           // clave XTEA
  34.  
  35.  
  36. char encripted_buffer[8];        // buffer de 8 bytes para recibir los primeros 8 caracteres encriptados.
  37. char line [46];                 // buffer para construir una linea hex completa, desde ":" hasta el "CR"
  38. int  buffidx = 0;        // indice para buffer primario (desencriptado))
  39. int  lineidx = 0;        // indice para buffer constructor de lineas
  40. int1 lineconst = 0;      // bool para control de linea en contrucción o linea concluida.
  41.  
  42.  
  43.  
  44.  
  45. unsigned int atoi_b16(char *s);     // conversor de dos caracteres hex en un entero de 8 bits decimal
  46. void buffering();                   // Obtiene un paquete de 8 bytes desencriptados.
  47. void decipher(int32 v[2]);          // recibe 8 bytes encriptados por xtea y devuelve esos 8 bytes desencriptados.
  48. void load_program ();                    // constructor de lineas hex
  49. void graba();                      // procesador de lineas hex y grabación en la flash.
  50.  
  51.  
  52. #org 0xc80,0xc82                  // vector de arranque de la aplicación a cargar. Esto será sobreescrito por el "goto" inicial de la app cargada
  53. void main_program (void) {
  54.      while(1);    
  55. }                                    // fin vector de arranque
  56.  
  57.  
  58. void main(void) {
  59.    OSCCON=CLK_16;                       // configuracion oscilador
  60.    OSCTUNE=0b11000000;                  // fonfig oscilador.  
  61.    PLLEN=TRUE;                          // config oscilador    64 Mhz.
  62.    set_tris_a(0b00111111);              // definidos los puertos segun la configuración de la placa y persiféricos conectados en la cpu donde se va a cargar este bootloader
  63.    set_tris_b(0b10111111);  
  64.    set_tris_c(0b01111101);
  65.    CREN = 0;                           // Deshabilitada la recepción por puerto rs232. ( Si algo envía datos, no nos llena el fifo))
  66.    delay_ms(1000);                    // pausa de 1 segundo para estabilizar arranque, alimentación, osciladores.
  67.    
  68.       fprintf(LCD,"SD2");
  69.       fprintf(LCD,"CL");
  70.    
  71.      
  72.      
  73.      
  74.      
  75.      
  76.      
  77.      
  78.    
  79.    if(!input(PUSH_BUTTON))                          // si está pulsado entramos en modo bootloader.
  80.    {
  81.      
  82.       fprintf(LCD,"TTWaiting for download");        // mensaje en el lcd.
  83.       fputc(0,LCD);                                // caracter null para el lcd (requerido por el lcd);)
  84.       delay_ms(100);                              // espera de tráfico concluido hacia el lcd.
  85.       fputc (XON,TX);                           // purgamos cualquier dato que pueda haber retenido en el cargador coolterm, realterm, etc..
  86.      
  87.       load_program();                                 //  recepcion, procesado y grabación del programa encriptado.
  88.      
  89.      
  90.    }
  91.  
  92.   main_program();                               // si no hemos pulsado saltamos al vector de arranque de la app.
  93. }
  94.  
  95. #int_global
  96. void isr(void) {                  
  97.  jump_to_isr(0x0c88);                     // redirige el vector de interrupción.
  98. }
  99.  
  100.  
  101.  
  102.  
  103.  
  104.  
  105.  
  106. void load_program () {                   // recepcion, procesado y grabación del programa encriptado.
  107.     lineidx = 0;                       // indice buffer de linea hex a cero.
  108.          
  109.     while(1) {                                // bucle secundario
  110.         while (1) {     //  bucle primario
  111.                  buffering();    // llenamos un buffer de 8 bytes de caracteres desencriptados.
  112.    
  113.                  for (i = 0; i <= 7; i++) {     // recorremos el buffer en busca del inicio de linea (:)
  114.                          if ((encripted_buffer[i] == ':') || (lineconst == 1)) {
  115.                          lineconst = 1;                                          // si lo encontramos indicamos que hay una linea en construcción
  116.                          line[lineidx++] = encripted_buffer[i];              // recorremos el buffer ya desencriptado y lo volcamos sobre el buffer line.
  117.                          if (line[lineidx - 1] == 0x0d) lineconst = 0;      // si en algun momento encontramos el caracter 0x0d cerramos la linea.
  118.                      }
  119.              if (lineconst == 0) break;     // si se ha completado una linea salimos del bucle for y dejamos el buffer actual intacto..
  120.            
  121.         }
  122.           if (lineconst == 0) break;     // si se ha completado una linea salimos del bucle while primario.
  123.              
  124.     }
  125.      
  126.      
  127.      graba();      // mandamos a procesar y a grabar la linea en la flash.
  128.      
  129.      // borrado de linea
  130.      for (i=0; i<=45;i++) line[i] = 255;    // vaciamos completamente la linea a 0xFF.
  131.        
  132.               // el ultimo buffer de 8 bytes, donde habiamos encontrado el 0x0d retorno de carro (fin de linea hex) aun contiene o puede contener mas caracteres
  133.              // que tenemos que utilizar.
  134.      
  135.                   // Por ello, habiéndolo dejado intacto volvemos a escanear el ultimo buffer donde se obtuvo el CR ya que seguramente contendrá el inicio de la linea siguiente..
  136.      lineidx = 0;  // ponemos indice idx de la linea en cero para que empiece a sobreescribirla.
  137.        
  138.      for (i = 0; i <= 7; i++) {     // recorremos el buffer en busca del inicio de la siguiente linea (:)
  139.              
  140.             if ((encripted_buffer[i] == ':') || (lineconst == 1)) {   // si lo encontramos abrimos nueva linea.
  141.             lineconst = 1;                                      
  142.             line[lineidx++] = encripted_buffer[i];    // volcamos el resto del buffer desde donde se ha encontrado ":"  .    
  143.             }
  144.         }  
  145.      
  146.     }    // y volvemos al bucle secundario .
  147.            
  148.           // este proceso se repetirá indefinidamente hasta que se haya completado la descarga.
  149.           // en la función graba();, es donde se detecta el fin de la carga cuando se recibe un tipo de linea = 0.)
  150.     }  
  151.    
  152.    
  153.    
  154.    
  155.  
  156.    
  157.  
  158.  
  159.  
  160.  
  161.  
  162. void graba() {
  163.     h_addr = 0;                     // iniciamos h_addr a cero (16 bits superiores de la dirección de la flash)
  164.     int p = 0;                     // control local de la función.
  165.  
  166.     if (line[0] == ':') {             // comprobamos que el primer caracter sea el inicio de linea (:)
  167.          count = atoi_b16 (&line[1]);  // Cargamos en Count, el numero de bytes que hay que grabar en la flash. (Atoi nos convierte dos caracteres hex en un entero de 8 bits)
  168.          l_addr = make16(atoi_b16(&line[3]),atoi_b16(&line[5]));  // cargamos la direccion de la memoria flash donde hay que grabar estos datos.
  169.          line_type = atoi_b16 (&line[7]);                         // cargamos el tipo de linea al que se refiere.
  170.          addr = make32(h_addr,l_addr);                            // construimos addres de 32 bits para direccionar la flash.
  171.          
  172.          int left = (count * 2) + 9;                         // Count contiene el numero de enteros de 8 bits que hay que grabar, son dos caracteres por entero, por eso multiplicamos su valor por dos.
  173.                                                             //, le sumamos 9 por que son los caracteres del principio de la linea ":",numero de bytes "00", address, "0000", tipo de linea "00", son 9 caracteres
  174.                                                           // Aqui lo usamos para saber el numero de bytes que hay que meter en checksum, mas abajo también es utilizado por el buffer Data
  175.              // ahora Left contiene la posición del primer caracter de checksum.
  176.          
  177.          
  178.          
  179.          int checksum = 0;                             // valor inicial a checksum.
  180.          for (i=1; i<left; i+=2)            // el checksum se verifica con los caracteres desde posicion 1 de la linea, hasta el final excepto los dos ultimos valores (que son el propio checksum). tampoco se tiene en cuenta el LF ni el CR.
  181.             checksum += atoi_b16 (&line[i]);  // concatenamos y sumamos todos los valores arriba indicados.
  182.          checksum = 0xFF - checksum + 1;     // restamos a 255 el valor que nos da la concatenación y le sumamos 1. El resultado ha de coincidir con el entero
  183.                                                 // que suministran los dos ultimos caracteres.
  184.          if (checksum != atoi_b16 (&line[left])){   // comparamos
  185.             fprintf(LCD,"TTChecksum ERROR!\r\n");   // si no coincide cancelamos la operación.
  186.             fputc(0,LCD);              
  187.             delay_ms(10);
  188.            
  189.             for(;;);                               // fin de programa por error de checksum.
  190.            }  
  191.              
  192.                // si checksum es ok continuamos.....
  193.          
  194.          
  195.          if (line_type == 1) {                       // si el tipo de linea es "1" significa que hemos concluido la carga completa del programa.                        
  196.             delay_ms(100);                              
  197.             fprintf(LCD,"TTSuccessfull update!\r\n");    // indicamos fin de carga con éxito.
  198.             fputc(0,LCD);            
  199.             fputc(XON,TX);
  200.             delay_ms(1000);
  201.             reset_cpu();                               // y reiniciamos para que arranque el nuevo programa.
  202.            }  
  203.                
  204.          
  205.          else if (line_type == 4) // si el tipo de linea es "4" es por que tenemos que usar una dirección de más de 16 bits de datos, obtenemos de esta linea los otros 16 bits, y saltamos al final del bucle para pedir la siguiente linea.
  206.                h_addr = make16(atoi_b16(&line[9]), atoi_b16(&line[11]));  // ya tenemos en h_addr los otros 16 bits.
  207.            
  208.            
  209.          else if (line_type == 0) {  // si el tipo de linea es "0", se trata de una linea relevante de datos para la flash.
  210.            
  211.          
  212.              if ((addr >= 0xc80) && (addr < getenv("PROGRAM_MEMORY")))  {        // Solo si la posicion de memoria está comprendida entre la zona reservada grabamos la flash
  213.                                
  214.         for (i = 9,dataidx=0; i < left; i += 2)           // a partir del caracter 9 de una linea, hasta la posicion "left" calculada segun "count" (numero de bytes)
  215.                     data[dataidx++]=atoi_b16(&line[i]);        // cargamos en el bucle DATA los enteros ya convertidos de los caracteres. Aunque no está lleno, data es un array de 32 bytes  
  216.                                                             // debido a que la función write_program_memory en el caso de este cpu, trabaja por bloques de 32 bytes
  217.         write_program_memory(addr, data, count);       // Grabamos en la flash el bloque completo de 32 bytes.
  218.               }                                   // notese que hemos elegido que el programa ocupa a partir de la dirección 0xc80. Es el multiplo de 64 (flash_erase_size" mas cercano)
  219.                                                  // que tengo por encima de lo minimo que ocupa este bootloader + una reserva de espacio por si el dia de mañana tuviese que actualizar el propio bootloader.
  220.           }                                    // de modo que esta función trabajará de forma mas optima por que borrará todo el bloque de 64 bytes en cada operación multiplo  
  221.     }                                        // y eso garantiza que no queden datos residuales de anteriores versiones del programa cargado.
  222. }                                           // Si esto no se cumple, sería prudente efectuar un borrado completo de la zona reservada en flash antes de cargar un programa.
  223.  
  224.  
  225.  
  226.    
  227.    
  228.    
  229.    
  230.  
  231.  
  232. void buffering() {         //  XTEA trabaja por bloques de 8 bytes, recibimos el firmware de 8 en 8 bytes,  
  233.    
  234.     fputc (XON,TX);   //  indicamos al software externo que proceda a enviar datos.  
  235.                             // llenamos el buffer inicial con 8 caracteres desencriptados...
  236.         buffidx = 0;       // indice del buffer de 8 bytes para el XTEA
  237.         CREN = 1;         // habilito la recepción de datos en el modulo usart de la cpu.
  238.        
  239.    
  240.         do {                                        // recibimos el primer bloque de 8 bytes.                  
  241.          encripted_buffer[buffidx] = fgetc(TX);  // con este bucle recibiremos 7 bytes, el octavo lo leeremos justo después del XOFF ya que siempre le da tiempo de enviar un byte mas.
  242.         } while (buffidx++ <= 5);               // ya que al solicitar XOFF a coolterm, siempre le ha dado tiempo a enviar un ultimo byte.
  243.     fputc (XOFF,TX);                       // enviamos solicitud a software externo para que pause el envío de caracteres.
  244.     encripted_buffer[7] = fgetc(TX);      // cogemos el octavo byte que siempre se envía tras la peticion de parada                    
  245.      
  246.     CREN = 0;                              // detenemos el puerto de recepcion del microcontrolador.
  247.      decipher(encripted_buffer);           // desencriptamos por Xtea de 128 bits. Ahora tenemos en el mismo buffer 8 bytes desencriptados.    
  248. }
  249.    
  250.  
  251.  
  252.  
  253. void decipher(int32 v[2]) {                // tiny XTEA 128 bits.
  254.        
  255.         int32 v0 = v[0], v1 = v[1], delta = 0x9E3779B9, sum = delta * 32;     // 32 rondas
  256.    
  257.     for (i = 0; i < 32; i++)
  258.         {
  259.                 v1 -= (((v0 << 4) ^ (v0 >> 5)) + v0) ^ (sum + key[(sum >> 11) & 3]);
  260.                 sum -= delta;
  261.                 v0 -= (((v1 << 4) ^ (v1 >> 5)) + v1) ^ (sum + key[sum & 3]);
  262.         }
  263.       v[0] = v0; v[1] = v1;     // asignamos para cargar en el buffer.
  264. }
  265.  
  266.  
  267. unsigned int atoi_b16(char *s) {    // obtiene un numero entero de 8 bits a partir de dos caracter headecimales.-
  268.    unsigned int result = 0;
  269.    int i;
  270.  
  271.    for (i=0; i<2; i++,s++)  {
  272.           if (*s >= 'A')
  273.                  result = 16*result + (*s) - 'A' + 10;
  274.          else
  275.                  result = 16*result + (*s) - '0';
  276.    }
  277.  
  278.    return(result);
  279. }



 Y aqui para encriptar desde el pc. Para encriptar se escribe en la consola:  xtea fichero.hex -e
y para desencriptar xtea fichero.hex -d

Código: C++
  1. #include <iostream>
  2. #include <fstream>
  3. #include <stdint.h>
  4. #include <string.h>
  5. using namespace std;
  6.  
  7. #define BLOCK_SIZE 8 //XTEA uses 64-bit blocks, 64 bits is 8 bytes
  8.  
  9. unsigned int key[4] = { 0xFACE, 0xDEAD, 0xBABE, 0xD00D };
  10. uint32_t orgval;
  11. uint32_t endval;
  12.  
  13.  
  14.  
  15. //XTEA block cipher - code from Wikipedia
  16. //https://en.wikipedia.org/wiki/XTEA
  17.  
  18. void encipher(unsigned int num_rounds, uint32_t v[2], uint32_t const key[4])
  19. {
  20.         unsigned int i;
  21.         uint32_t v0 = v[0], v1 = v[1], sum = 0, delta = 0x9E3779B9;
  22.         for (i = 0; i < num_rounds; i++)
  23.         {
  24.                 v0 += (((v1 << 4) ^ (v1 >> 5)) + v1) ^ (sum + key[sum & 3]);
  25.                 sum += delta;
  26.                 v1 += (((v0 << 4) ^ (v0 >> 5)) + v0) ^ (sum + key[(sum >> 11) & 3]);
  27.         }
  28.         v[0] = v0; v[1] = v1;
  29. }
  30.  
  31. void decipher(unsigned int num_rounds, uint32_t v[2], uint32_t const key[4])
  32. {
  33.         unsigned int i;
  34.         uint32_t v0 = v[0], v1 = v[1], delta = 0x9E3779B9, sum = delta * num_rounds;
  35.         for (i = 0; i < num_rounds; i++)
  36.         {
  37.                 v1 -= (((v0 << 4) ^ (v0 >> 5)) + v0) ^ (sum + key[(sum >> 11) & 3]);
  38.                 sum -= delta;
  39.                 v0 -= (((v1 << 4) ^ (v1 >> 5)) + v1) ^ (sum + key[sum & 3]);
  40.         }
  41.         v[0] = v0; v[1] = v1;
  42. }
  43.  
  44. void convert(uint32_t x[2]) {
  45.         orgval = x[0];
  46.         endval = x[1];
  47.  
  48.  
  49. }
  50.  
  51. void xtea(char filePath[], bool boolEncrypt)
  52. {
  53.         //Open file
  54.         fstream file(filePath, ios::in | ios::out | ios::binary);
  55.         cout << endl << "Opening file: " << filePath << endl;
  56.         if (!file) //Check if file is correctly opened
  57.         {
  58.                 cout << "File " << filePath << " cannot be opened" << endl;
  59.                 return;
  60.         }
  61.  
  62.         cout << "File open" << endl;
  63.         file.seekg(0, ios::end);
  64.         unsigned fileSize = file.tellg(); //Get file size
  65.         cout << "File size: " << fileSize << " bytes" << endl;
  66.         file.seekg(ios::beg);
  67.         file.clear();
  68.  
  69.         //Calculate number of blocks to be encrypted/decrypted
  70.         int blockNumber = fileSize / BLOCK_SIZE;
  71.         if (fileSize % BLOCK_SIZE != 0) { ++blockNumber; }
  72.         cout << "Number of blocks: " << blockNumber << endl;
  73.  
  74.         //Decalre data array for file operations
  75.         unsigned char dataArray[BLOCK_SIZE];
  76.         unsigned filePosition = file.tellg();
  77.  
  78.         if (boolEncrypt) { cout << "Starting encryption" << endl; }
  79.         else { cout << "Starting decryption" << endl; }
  80.         for (int i = 0; i < blockNumber; i++)
  81.         {
  82.                 //Get data from file
  83.                 file.seekg(filePosition);
  84.                 file.read((char*)dataArray, BLOCK_SIZE);
  85.  
  86.      
  87.  
  88.                 //Encrypt/decrypt
  89.                 if (boolEncrypt) { encipher(32, (uint32_t*)dataArray, key); }
  90.                 else { decipher(32, (uint32_t*)dataArray, key); }
  91.  
  92.                 //Write to file
  93.                 file.seekp(filePosition);
  94.                 file.write((char*)dataArray, BLOCK_SIZE);
  95.  
  96.  
  97.  
  98.                 //Zero out the data array and increase the pos counter
  99.                 memset(dataArray, 0, BLOCK_SIZE);
  100.                 filePosition += BLOCK_SIZE;
  101.         }
  102.         //Close file
  103.         file.close();
  104.         cout << "Closing file" << endl;
  105.         if (boolEncrypt) { cout << "File " << filePath << " has been encrypted" << endl; }
  106.         else { cout << "File " << filePath << " has been decrypted" << endl; }
  107. }
  108.  
  109.  
  110.  
  111. int main(int argc, char *argv[])
  112. {
  113.         if (argc != 3)
  114.         {
  115.                 if ((argc == 2) && (string(argv[1]) == "-h"))
  116.                 {
  117.                         cout << endl << "Usage: " << "[" << argv[0] << "]" << " [file] [-e/-d]" << endl;
  118.                         cout << "[file] is path to the file you want to encrypt/decrypt" << endl;
  119.                         cout << "[-e/-d] choose one to encrypt/decrypt" << endl;
  120.                         cout << endl << "Example usage: XTEA.exe photo.jpg -e" << endl;
  121.                 }
  122.                 else { cout << endl << argv[0] << " You have entered invalid number of parameters" << endl; }
  123.                 return 1;
  124.         }
  125.  
  126.         bool encrypt = false;
  127.         if ((string(argv[2]) != "-e") && ((string(argv[2]) != "-d"))) { cout << "Invalid parameter " << argv[2] << endl; return 1; }
  128.         if (string(argv[2]) == "-e") { encrypt = true; }
  129.  
  130.         //Encrypt/decrypt
  131.         xtea(argv[1], encrypt);
  132.         return 0;
  133. }



« Última modificación: 24 de Septiembre de 2017, 13:26:12 por remi04 »

Desconectado planeta9999

  • Moderadores
  • DsPIC30
  • *****
  • Mensajes: 3520
    • Pinballsp
Re:Bootloader
« Respuesta #20 en: 24 de Septiembre de 2017, 13:37:53 »
 

Yo quitaría el pulsador para entrar en modo boot.

Si es por tarjeta SD, se chequea la existencia de la tarjeta, y que tenga el archivo a cargar, si no lo encuentra salta a la aplicación de usuario, si existe.

Si es por un puerto de comunicaciones, USB, Serie, CAN bus, Ethernet, compruebo comunicaciones durante un lapso de tiempo (10-20 segundos por ejemplo), si no hay comunicación, salto a la aplicación de usuario, si existe. Si hay comunicación se queda en modo boot esperando comandos para cargar el firmware.

Lo del pulsador, siempre me ha parecido algo totalmente prescindible, nunca monto en mis placas un pulsador para entrar en modo actualización, salvo en una placa que diseñé hace tiempo con un STM32 porque esta entraba en modo DFU USB, no era un bootloader de usuario.

Además puedes aprovechar y reservar algunas direcciones de la flash, para guardar datos que identifiquen la placa y el producto. Por ejemplo Número de serie único por placa, Código de producto, Versión de firmware y algún código de protección para bloquear placas piratas, así lo tenía yo en el bootloader que hice para PIC32.

En mi situación actual, que ya solo trabajo con ARM, tanto los Kinetis como los STM32 tienen de fábrica grabado un número de serie único por microcontrolador, y el resto lo tengo todo con el bootloader uTasker.
« Última modificación: 24 de Septiembre de 2017, 13:46:49 por planeta9999 »

Desconectado remi04

  • PIC24F
  • *****
  • Mensajes: 657
Re:Bootloader
« Respuesta #21 en: 24 de Septiembre de 2017, 14:30:13 »
Gracias, planeta9999.

  Lo de esperar una transmision no me es viable por que es una aplicacion que no debe demorar mas de 1 segundo en iniciar. El pulsador lo tiene la aplicacion, ya que se maneja todo, menus, ajustes, etc con un unico pulsador. Por ello lo aprovecho para el boltloader. Aunque sinceramente tampoco soy amigo de usarlo asi. Pero es la opcion mas viable.

  Lo del numero de serie lo cargo en la eeprom interna con el boltloader al cargarlo con el pickit2.  Luego tanto eeprom como el codigo va todo en code protect.

   Eso no aparece en el codigo que he puesto arriba por que para el caso que ocupa es superfluo ponerlo ahi. 


 

anything