1. Tämä sivusto käyttää keksejä (cookie). Jatkamalla sivuston käyttämistä hyväksyt keksien käyttämisen. Lue lisää.

C-koodin optimointi apuja?(microchip)

Viestiketju Vapaata keskustelua -osiossa. Ketjun avasi JoniS 07.11.2014.

  1. JoniS

    JoniS Active member

    Liittynyt:
    06.10.2008
    Viestejä:
    2,951
    Kiitokset:
    261
    Pisteet:
    93
    elikkäs loppui muisti kesken pic16f690:sta ja olisi tarvetta lyhentää koodia jonkun verran, koska lisää pitäisi saada vielä aika tavalla jotta projektista saisi jotain irtikin...

    ehkäpä joku osaisi auttaa hieman selventämään muutamista esimerkeistä mikä loppu pelissä olisi muistin kannalta paras...(joo kokeilemalla selviää, mutta kun en itse omista tuota ohjelmointi palikkaa taikka kunnon kääntäjää vielä...)

    myös kaipaisin kommenttia ihan tuosta koodista ylipäätään, kritiikki tervetullutta siis.


    tässä siis tämän hetkinen, yksi monista kohdista missä varmasti olisi parantamisen varaa....
    Koodi:
    void naytto() {
    
        sprintf(str_lcd, " %2d.%2dV", akku / 100, akku % 100);
        print_xy(0, 1, str_lcd);
        sprintf(str_lcd, "  %2d.%2dV ", vahvari / 100, vahvari % 100);
        print_xy(0, 10, str_lcd);
       
        if(alarivisaato < 3)
        alarivisaato = alarivisaato + 1;
        else
        alarivisaato = 1;
       
        if (alarivisaato == 1) {
            sprintf(str_lcd, "   %02d:%02d:%02d    ", hour, min, sec);
            print_xy(1, 0, str_lcd);
        }
    
        if (alarivisaato == 2) {
            sprintf(str_lcd, "Akku    Vahvari");
            print_xy(1, 0, str_lcd); 
        }
        if (alarivisaato == 3){
            vahvkoko = (int)EEPROM_READ(0x00);
            vahvjaannos = (int)EEPROM_READ(0x01);
            sprintf(str_lcd, "    %2d.%2dV     ", vahvkoko, vahvjaannos);
            print_xy(1, 0, str_lcd);
        }

    tässä yksi vaihtoehto?
    Koodi:
    void naytto() {
    
        sprintf(str_lcd, " %2d.%2dV", akku / 100, akku % 100);
        print_xy(0, 1, str_lcd);
        sprintf(str_lcd, "  %2d.%2dV ", vahvari / 100, vahvari % 100);
        print_xy(0, 10, str_lcd);
       
        if(alarivisaato < 3)
        alarivisaato = alarivisaato + 1;
        else
        alarivisaato = 1;
       
        if (alarivisaato == 1) {
            sprintf(str_lcd, "   %02d:%02d:%02d    ", hour, min, sec);
        }
    
        if (alarivisaato == 2) {
            sprintf(str_lcd, "Akku    Vahvari");
            
        }
        if (alarivisaato == 3){
            vahvkoko = (int)EEPROM_READ(0x00);
            vahvjaannos = (int)EEPROM_READ(0x01);
            sprintf(str_lcd, "    %2d.%2dV     ", vahvkoko, vahvjaannos);
            
        }
    print_xy(1, 0, str_lcd);
    
    vai olisiko paras tehdä oma funktionsa printtauksen kordinaateille, jotta sitä voisi käyttää kaikkialta?(en kyllä mene takuuseen onnistuuko kordinaattien anto eri funktiossa, kuin siinä missä sanotaan mitä printataan) ->
    Koodi:
    void naytto() {
    
        sprintf(str_lcd, " %2d.%2dV   %2d.%2dV", akku / 100, akku % 100, vahvari / 100, vahvari % 100);
        print();
       
        if(alarivisaato < 3)
        alarivisaato = alarivisaato + 1;
        else
        alarivisaato = 1;
       
        if (alarivisaato == 1) {
            sprintf(str_lcd, "   %02d:%02d:%02d    ", hour, min, sec);
        }
        if (alarivisaato == 2) {
            sprintf(str_lcd, "Akku    Vahvari");
        }
        if (alarivisaato == 3){
            vahvkoko = (int)EEPROM_READ(0x00);
            vahvjaannos = (int)EEPROM_READ(0x01);
            sprintf(str_lcd, "    %2d.%2dV     ", vahvkoko, vahvjaannos);
            print(int joku = 1);
        }
    
    void print(){
    
       if(joku == 1) 
            print_xy(1, 0, str_lcd); //printtaus alariville
            return;
       else
           print_xy(0, 1, str_lcd); //printtaus yläriville
    }

    mitä tapaa itse suosisitte? nuo 2 esimerkkiä toisista tavoista näpytin nopeasti niin älkää paneutuko pieniin virheisiin niissä jos näettä, idea kuitenkin pitäisi käydä selväksi.
     
  2.  
  3. R4ndom1

    R4ndom1 Regular member

    Liittynyt:
    06.06.2013
    Viestejä:
    588
    Kiitokset:
    52
    Pisteet:
    38
    AD on tuskin paras paikka jos kaipaa ohjelmointiapua. Sulla on monta ehtolausetta peräkkäin, joista kuitenkaan vain yksi voi olla tosi, joten kannattasiko käyttää else if:iä tai switch casea? Laita koko koodi näkyviin, koska eipä tuosta paljoa ota selvää.
     
    JoniS kiitti tästä.
  4. JoniS

    JoniS Active member

    Liittynyt:
    06.10.2008
    Viestejä:
    2,951
    Kiitokset:
    261
    Pisteet:
    93
    Switch caseen voisi kyllä nuo siirtää, samaten osan muusta koodista mitkä toteutettu while(asd==x) tällä hetkellä..(jotenkin jäänyt päälle noitten while looppien tekeminen switchin sijaan.)

    Täytyy myöhemmin laittaa loput koodista jahka pääsen kotia ja saan kirjoitettua pienet dokumentaatiot sinne selventämään asioita.
     
  5. xbkrypt0n

    xbkrypt0n Active member

    Liittynyt:
    16.06.2010
    Viestejä:
    3,154
    Kiitokset:
    120
    Pisteet:
    73
    Switch casesta meinasin mainita, mutta en sitten tiedä viekö koodi yhtään sen vähemmän tilaa niitä käyttämällä.

    Onko nuo vahvkoko ja vahvjaannos kovin tärkeitä muuttujia? Voisi suoraan pistää printtiin
    sprintf(str_lcd, " %2d.%2dV ", (int)EEPROM_READ(0x00), (int)EEPROM_READ(0x01)
    ja jättää muuttujat kokonaan varaamatta.

    alarivisaato = alarivisaato + 1 vaikuttaa myös aika ikävältä (++). Onko sitten vaikutusta tilantarpeeseen? EOS.

    Koko koodi pitäisi tosiaan laittaa jakoon, että osaisi mitään tuohon sanoa. Google Drive on ihan näppärä paikka jakaa dokumentteja jos ei jaksa mitään gittiä/tms. väsäillä.

    E: Se koodihan vie paljon vähemmän tilaa käännettynä kuin selkokielisenä.
     
    Viimeksi muokattu: 07.11.2014
    JoniS kiitti tästä.
  6. JoniS

    JoniS Active member

    Liittynyt:
    06.10.2008
    Viestejä:
    2,951
    Kiitokset:
    261
    Pisteet:
    93
    väsäilin switch case "version" koodista, mikä on huomattavasti selkeämpi lukea.

    tosiaan koko jutun juju on lukea akun ja vahvistimen jännitettä autossa, ja sammuttaa pic:iltä lähtö mikä antaa vahvistimelle heräten virran jos jännite tipahtaa liian alas määritetyksi ajaksi.(tietty C-koodin harjoittelu samalla)
    tila vain loppui ennenkuin sain edes toisen timerin asetettua millä sammuttaisin tuon lähdön.

    Koodi:
    /*
    * File:   jannite.c
    * Author: Joni
    *
    * Created on 7. marraskuuta 2014, 20:11
    */
    
    #include <xc.h>
    #include <htc.h>
    #include <stdio.h>
    
    //CONFIG 16f690
    #pragma config FOSC = INTRCCLK    // Oscillator Selection (INTOSC oscillator: I/O function on ra4/5)
    #pragma config WDTE = OFF        // Watchdog Timer Enable (WDT disabled)
    #pragma config PWRTE = ON      // Power-up Timer Enable (PWRT enabled)
    #pragma config MCLRE = OFF       // MCLR Pin Function Select (MCLR/VPP pin function is not MCLR)
    #pragma config CP = OFF        // Flash Program Memory Code Protection (Program memory code protection is disabled)
    #pragma config CPD = OFF
    #pragma config BOREN = OFF      // Brown-out Reset Enable (Brown-out Reset disabled)
    #pragma config IESO=OFF
    
    //MUUTA
    #define RS RC1
    #define EN RC0
    #define DATABITS PORTB
    #define MENU RC4
    #define ENTER RC5
    #define PLUS RC6
    #define MIINUS RC7
    #define AKKU7 0x9D
    #define AKKU7GO 0x9F
    #define VAHV6 0x99
    #define VAHV6GO 0x9b
    
    
    void ajansaato();
    void tulostus();
    void menu();
    void remsaadot();
    
    unsigned int msec, sec = 0, min = 15, hour = 8;
    int scroll = 1;
    int remscroll = 1;
    int alarivisaato = 0;
    char str_lcd[16];
    int akku, vahvari;
    int remoteout = 0;
    int autorem = 0;
    int autoremout = 1;
    int autoremenable = 1;
    int vahvautorem = 1200;
    int vahvkoko, vahvjaannos;
    int alkuasetus;
    
    static void interrupt isr(void) //keskeytys
    {
        if (T0IF) {
            TMR0 = 156;
            T0IF = 0;
            OPTION_REG = 0x00;
    
            if (msec < 10000)
                msec++;
            else {
                msec = 0;
                sec++;
            }
            if (sec > 59) {
                sec = 0;
                min++;
            }
            if (min > 59) {
                min = 0;
                hour++;
            }
            if (hour > 23)
                hour = 0;
    
        }
    }
    
    //NÄYTTÖ
    
    void delay_ms(int time) {
        int i, j;
        for (i = 0; i < time; i++)
            for (j = 0; j < 100; j++);
    
    }
    
    void LCD_STROBE(void) {
        EN = 1;
        delay_ms(2);
        EN = 0;
    }
    
    void data(unsigned char c) {
        RS = 1;
        delay_ms(1);
    
        DATABITS = c;
        LCD_STROBE();
        DATABITS = (c << 4);
        LCD_STROBE();
    }
    
    void cmd(unsigned char c) {
        RS = 0;
        delay_ms(1);
    
        DATABITS = c & 0b11110000;
        LCD_STROBE();
        DATABITS = (c << 4) & 0xF0;
        LCD_STROBE();
    }
    
    void lcd_init(void) {
        delay_ms(15);
        RS = 0;
        DATABITS = 0x20;
        LCD_STROBE();
    
        cmd(0x28);
        cmd(0x0c);
        cmd(0x01);
        cmd(0x06);
    }
    
    void print_xy(int x, int y, const char *q) {
        if (y == 0)
            cmd(0xc0 + x);
        if (y == 1)
            cmd(0x80 + x);
        while (*q) {
            data(*q++);
        }
    }
    
    void putc_xy(int x, int y, unsigned char c) {
        if (y == 0)
            cmd(0xc0 + x);
        if (y == 1)
            cmd(0x80 + x);
        data(c);
    
    }
    
    //NÄYTTÖ loppu
    
    void main() {
    
        unsigned int TILA = 1;
        int mode = 0;
    
        // <editor-fold defaultstate="collapsed" desc="porttien alustus">
        /* Initial Port Used */
        TRISA = 0b00001111; //asetetaan PORTA
        TRISB = 0x00; //asetetaan PORTB
        TRISC = 0xFC; //asetetaan PORTC
        ANSEL = 0x80;
        ANSELH = 0x00;
        PORTA = 0b00100000; //portin nollaus
        PORTB = 0x00; //portin nollaus
        PORTC = 0x00; //portin nollaus// </editor-fold>
    
        /*kellokeskeytys*/
        OSCCON = 0x77;
        OSCTUNE = 0x0F;
        OPTION_REG = 0x00;
        TMR0 = 156;
        T0IE = 1;
        GIE = 1;
    
        //näytön alustus
        delay_ms(50);
        lcd_init();
    
        //alku asetukset ensimmäisellä käynnitys kerralla
        alkuasetus = EEPROM_READ(0x05);
        if (alkuasetus == 0) {
            remsaadot();
            alkuasetus = 1;
            EEPROM_WRITE(0x05, alkuasetus);
        }
    
        while (1) {
    
            // <editor-fold defaultstate="collapsed" desc="Muunnos">
            //analogi muunnosohjelma
            switch (TILA) {
                case 1: if (mode == 0) {
                        ADCON0 = AKKU7;
                        delay_ms(2);
                        ADCON0 = AKKU7GO;
                        TILA = 2;
                    }
                    if (mode == 1) {
                        ADCON0 = VAHV6;
                        delay_ms(2);
                        ADCON0 = VAHV6GO;
                        TILA = 2;
                    }
                    break;
    
                case 2: if (ADCON0 & 0x02) {
                        TILA = 2;
                    } else {
                        if (mode == 0)
                            akku = (float) (ADRESH * 256 + ADRESL)*1.525;
                        if (mode == 1)
                            vahvari = (float) (ADRESH * 256 + ADRESL)*1.525;
                        TILA = 3;
                    }
                    break;
    
                case 3: if (mode == 0)
                        mode = 1;
                    else mode = 0;
                    TILA = 1;
                    break;
                default:TILA = 1;
            }// </editor-fold>
    
            tulostus();
    
            if (MENU == 0) {
                menu();
            }
            if (ENTER == 0) {
                tulostus();
            }
    
        }
    }
    
    void menu() {
    
                sprintf(str_lcd, "  enter to set  ");
                print_xy(1, 0, str_lcd);
    
        while (1) {
            switch (scroll) {
    
                case 1:
                    sprintf(str_lcd, "<<   remote   >>");
                    print_xy(0, 1, str_lcd);
                
                    if (PLUS == 0 || MIINUS == 0) {
                        scroll = 2;
                        delay_ms(100);
                    }
                    if (ENTER == 0) {
                        remsaadot();
                    }
                    if (MENU == 0) {
                        return;
                    }        
                    break;
                case 2:
                    sprintf(str_lcd, "<<   Clock   >>");
                    print_xy(0, 1, str_lcd);
                
                    if (PLUS == 0 || MIINUS == 0) {
                        scroll = 1;
                        delay_ms(100);
                    }
                    if (ENTER == 0) {
                        ajansaato();
                    }
                    if (MENU == 0) {
                        return;
                    }
                    break;
            }
    
        }
    }
    
    void remsaadot() {
    
        delay_ms(200);
        while (1) {
            switch (remscroll) {
                case 1:
                    sprintf(str_lcd, "<<   remote   >");
                    print_xy(0, 1, str_lcd);
    
                    if (MIINUS == 0 || PLUS == 0 && remoteout == 1) {
                        remoteout = 0;
                        while (MIINUS == 0 || PLUS == 0);
                    }
                    if (MIINUS == 0 || PLUS == 0 && remoteout == 0) {
                        remoteout = 1;
                        while (MIINUS == 0 || PLUS == 0);
                    }
                    RA5 = remoteout;
                    EEPROM_WRITE(0x03, remoteout);
    
                    if (remoteout == 0) {
                        sprintf(str_lcd, "    rem off   ");
                        //print_xy(1, 0, str_lcd);
                    }
                    if (remoteout == 1) {
                        sprintf(str_lcd, "    rem  on  ");
                        //print_xy(1, 0, str_lcd);
                    }
                    if (MENU == 0) {
                        delay_ms(100);
                        return;
                    }
                    if (ENTER == 0) {
                        remscroll = 2;
                    }
                    print_xy(1, 0, str_lcd);
                    break;
    
                case 2:
                    sprintf(str_lcd, "<  auto remote >");
                    print_xy(0, 1, str_lcd);
    
                    if (MIINUS == 0 || PLUS == 0 && autoremout == 1) {
                        autoremout = 0;
                        while (MIINUS == 0 || PLUS == 0);
    
                    }
                    if (MIINUS == 0 || PLUS == 0 && autoremout == 0) {
                        autoremout = 1;
                        while (MIINUS == 0 || PLUS == 0);
                    }
                    EEPROM_WRITE(0x02, autoremout);
    
                    if (autoremout == 0) {
                        sprintf(str_lcd, " auto.rem off   ");
                        print_xy(1, 0, str_lcd);
                    }
                    if (autoremout == 1) {
                        sprintf(str_lcd, " auto.rem  on  ");
                        print_xy(1, 0, str_lcd);
                    }
                    if (MENU == 0) {
                        delay_ms(100);
                        return;
                    }
                    if (ENTER == 0) {
                        remscroll = 3;
                    }
                    break;
    
                case 3:
                    sprintf(str_lcd, "< auto rem.raja >");
                    print_xy(0, 1, str_lcd);
    
                    sprintf(str_lcd, "    %2d.%2dV   ", vahvautorem / 100, vahvautorem % 100);
                    print_xy(1, 0, str_lcd);
    
                    if (PLUS == 0 && vahvautorem < 1560) {
                        vahvautorem = vahvautorem + 10;
                        delay_ms(100);
                        while (PLUS == 0);
                    }
    
                    if (MIINUS == 0 && vahvautorem > 500) {
                        vahvautorem = vahvautorem - 10;
                        delay_ms(100);
                        while (MIINUS == 0);
                    }
                    if (ENTER == 0) {
                        vahvkoko = vahvautorem / 100;
                        vahvjaannos = vahvautorem % 100;
                        EEPROM_WRITE(0x00, vahvkoko);
                        delay_ms(5);
                        EEPROM_WRITE(0x01, vahvjaannos);
                        delay_ms(5);
                        return;
                    }
    
                    break;
    
            }
        }
    }
    
    void tulostus() {
    
        sprintf(str_lcd, " %2d.%2dV  %2d.%2dV ", akku / 100, akku % 100, vahvari / 100, vahvari % 100);
        print_xy(0, 1, str_lcd);
    
        if (alarivisaato < 3)
            alarivisaato++;
        else
            alarivisaato = 1;
    
        switch (alarivisaato) {
    
            case 1:
                sprintf(str_lcd, "   %02d:%02d:%02d    ", hour, min, sec);
                break;
            case 2:
                sprintf(str_lcd, "Akku    Vahvari");
                break;
            case 3:
                vahvkoko = (int) EEPROM_READ(0x00);
                vahvjaannos = (int) EEPROM_READ(0x01);
                sprintf(str_lcd, "    %2d.%2dV     ", vahvkoko, vahvjaannos);
                break;
        }
        print_xy(1, 0, str_lcd);
    }
    
    void ajansaato() {
        delay_ms(100);
        char str_lcd[16];
        unsigned int hourmin = 1;
        while (hourmin == 1) {
            print_xy(0, 1, "  Aseta tunnit   ");
            sprintf(str_lcd, "   %02d:%02d:%02d   ", hour, min, sec);
            print_xy(1, 0, str_lcd);
    
            if (PLUS == 0) {
                hour++;
                delay_ms(100);
            }
            if (MIINUS == 0) {
                hour--;
                delay_ms(100);
            }
            if (ENTER == 0) {
                hourmin++;
                delay_ms(100);
            }
            if (MENU == 0) {
                return;
            }
    
    
        }
        while (hourmin == 2) {
            print_xy(0, 1, " Aseta minuutit ");
            sprintf(str_lcd, "   %02d:%02d:%02d   ", hour, min, sec);
            print_xy(1, 0, str_lcd);
    
            if (PLUS == 0) {
                min++;
                delay_ms(100);
            }
            if (MIINUS == 0) {
                min--;
                delay_ms(100);
            }
            if (ENTER == 0) {
                hourmin++;
                sec = 0;
                print_xy(0, 1, "   onnistui!   ");
                delay_ms(2000);
            }
            if (MENU == 0) {
                return;
            }
        }
    }
    
    luultavasti jotain virhettä löytyy, mutta ei paneuduta niihin nyt, ohjelma kuitenkin toimi alkuperäisessä muodossa, mutta siihen ei voinut tilan puutteen takia lisätä enään yhtään mitään.
    TO-DO
    -toinen timeri missä muutetaan RA5 tilaa jos tietty ehto täyttyy ja katkaisu asetettu päälle.(kun vain mahtuisi...)
    -eepromista luku kun laitetaan virrat päälle.

    E: tosiaan nuo print komennot ottaa pirusti tilaa, pitäisi varmaan kokeilla printin cordinaateille rutiini väsätä mikä poistaisi turhan "print_xy(xxxx)" kirjoituksen joka väliin, kun kuitenkin ohjelman jokainen osa aloittaa printin ylä- tai alarivin alusta.
     
    Viimeksi muokattu: 07.11.2014
  7. xbkrypt0n

    xbkrypt0n Active member

    Liittynyt:
    16.06.2010
    Viestejä:
    3,154
    Kiitokset:
    120
    Pisteet:
    73
    putc_xy ei ilmeisesti ole missään käytössä? vahvkoko ja vahvjaannos näyttävät olevan turhia muuttujia.

    esim.
    vahvkoko = vahvautorem / 100;
    EEPROM_WRITE(0x00, vahvkoko);
    voinee korvata
    EEPROM_WRITE(0x00, vahvautorem / 100);

    Äkkiseltään sanoisin, että kannattaisi hankkia piiri josta löytyy vähän enemmän tallennustilaa. Tuossa on ilmeisesti huimat 7kB tilaa softalle.

    E: Kääntäjä voi optimoida koodia jo valmiiksi, eli vaikka se koodi näyttää pitkälle, niin se kääntäjä on tehnyt jo ne optimoinnit itse. Vaikka koodia siis saisikin lyhennettyä tai yleisesti optimoitua, niin softan koko ei välttämättä pienene mihinkään.
     
    JoniS kiitti tästä.
  8. JoniS

    JoniS Active member

    Liittynyt:
    06.10.2008
    Viestejä:
    2,951
    Kiitokset:
    261
    Pisteet:
    93
    put_xy ei tosiaan taida olla käytössä ollenkaan täytenee poistaa pienen lisätilan toivossa.

    hmmn, totta pystyisin ottamaan suoraan kokonais luvun ja jäännöksen "vahvautorem" muuttujasta ilman tarvetta kahdelle eri muuttujalle, tämä varmaan tuokin jonkun verran tilaa ainakin.(tämä typerä kortti ei siis osaa printata float lukua muuttujasta -> "%f, xxx" , vaan se on pakko tehdä keinotekoisesti ottamalla kokonaisluku ja jäännös...)
     
  9. Sakke88

    Sakke88 Active member

    Liittynyt:
    11.04.2004
    Viestejä:
    1,773
    Kiitokset:
    19
    Pisteet:
    68
    Ohjelmoinnissa on useita koulukuntia, mutta ainakin itse kuulun siihen, joka vältää swith-case rakenteita viimeiseen asti. 95% tapauksista switch-case rakenteella tehdään yksinkertaisesta asiasta monimutkainen.

    Omaan silmään koodissa näkyy olevan todella paljon toistoa eli sitä todennäköisesti voisi yksinertaistaa. Lyhentämällä/yksinkertaistamalla koodia siitä saadaan helpompi lukuista ja se myös mahdollistaa kääntäjän koodin optimoinnin.

    Ns. if-else shorthand-lauseke on omasta mielestäni erittäin kätevä.

    esim:
    if (MIINUS == 0 || PLUS == 0 && remoteout == 1) {
    remoteout = 0;
    while (MIINUS == 0 || PLUS == 0);
    }
    if (MIINUS == 0 || PLUS == 0 && remoteout == 0) {
    remoteout = 1;
    while (MIINUS == 0 || PLUS == 0);
    }
    lyhyemmin:

    if (MIINUS == 0 || PLUS ) {
    remoteout=remout?0:1;
    while (MIINUS == 0 || PLUS == 0);
    }
    tai

    if (alarivisaato < 3)
    alarivisaato++;
    else
    alarivisaato = 1;

    lyhyemmin:

    alarivisaato=alarivisaat<3?alarivisaato+1:1;



    On myös syytä miettiä tarviiko tiettyä funktioita kutsua joka välissä:

    if (PLUS == 0) {
    hour++;
    delay_ms(100);
    }
    if (MIINUS == 0) {
    hour--;
    delay_ms(100);
    }
    if (ENTER == 0) {
    hourmin++;
    delay_ms(100);
    }
    if (MENU == 0) {
    return;
    }

    Vai:

    if (PLUS == 0)
    hour++;
    if (MIINUS == 0)
    hour--;
    if (ENTER == 0)
    hourmin++;
    if (MENU == 0)
    return;

    delay_ms(100);


    Ja kun oikeasti lähdetään säästämään jokaisesta tavusta, niin kannattaa miettiä tarvitaanko stdio.h kirjastoa. Pelkällä printf-komennolla tulee usen aivan hyvin toimeen.
     
    JoniS kiitti tästä.
  10. R4ndom1

    R4ndom1 Regular member

    Liittynyt:
    06.06.2013
    Viestejä:
    588
    Kiitokset:
    52
    Pisteet:
    38
    Tuossa koodissa käytät paljon int:ejä, vaikka joihinki muuttujiin riittää char.
     
    JoniS kiitti tästä.
  11. jons81

    jons81 Regular member

    Liittynyt:
    29.07.2010
    Viestejä:
    229
    Kiitokset:
    12
    Pisteet:
    28
    Vilkaisin koodia nopeasti jo ennen viikkoloppua, mutta kiireiden takia en ehtinyt vastata.
    Koodin alussa alustat taulukon jonka kooksi asetetaan 16 tavua.
    char str_lcd[16];

    Koodissa talletat sprintf komennolla taulukkoon merkkijonoja joiden pituus on 16 merkkiä eli oletettavasti myöskin 16 tavua. Esimerkiksi: sprintf(str_lcd, "<< remote >>");

    Ainkin muutamien standardien mukaan sprintf lisää merkkijonon perään merkkijonon päättymismerkin '\0' joka tässä tapauksessa vuotaisi yli taulukosta. Mikä tarkalleenottaen on saamasi "muistin loppumisen" virheilmoitus? Toimiiko koodi paremmin jos lisäät taulukon koon 17 tavun mittaiseksi tai yli (olettaen että pisimmär merkkijonot mahduvat siihen)?

    Muutamien lähteiden mukaan ja kuten aiemminkin mainititin sprintf() funktio ja stdio.h kuluttavat melko paljon muistia microcontrollerilta.
     
    JoniS kiitti tästä.
  12. JoniS

    JoniS Active member

    Liittynyt:
    06.10.2008
    Viestejä:
    2,951
    Kiitokset:
    261
    Pisteet:
    93
    Siis ihan ohjelmalle varattu tila tuli täyteen, ei suostunut enään edes kääntäjä kääntämään koodia sen takia.(kaivan sen errorin myöhemmin) hommasin nyt kuitenkin tuon xc8 pro:n lisenssin ja sillä kääntää koodin sen ~35% pienempään tilaan joten mahtuu taas, tuo xc8 free ilmeisesti bloattaa asm koodia jonnin verran, minkä takia se olevinaan ei mahtunut.

    Jep nuo sprintf käskyt vei tuolla free kääntäjällä ~1.5% muistista per käyttökerta... Näyttö on 16x2 merkkiä max.

    Toivottavasti nyt vain mahtuisi tuo loppu koodi vielä tuonne jahka saan kirjoitettua kaiken tarvittavan.

    Anyway, iso kiitos kaikille neuvoista! En tosiaan ole c-koodin kanssa enempää kuin 3kk nyt touhunnut niin kaikki neuvot ovat tervettulleita.

    Esim. -> remoteout=remout?0:1; tuli ihan uutena tuttavuutena, ja päätyikin käyttöön muutamaan paikkaan kunhan sain sen ensiksi väännettyä kääntäjäni ymmärtämään muotoon -> x=(b==0)?1:0;
     

Jaa tämä sivu