-         

Ergebnis 1 bis 6 von 6

Thema: Inline Assembler - Variablenverwaltung / Warnungen

  1. #1
    Erfahrener Benutzer Roboter-Spezialist
    Registriert seit
    08.07.2006
    Ort
    Karlsruhe/München
    Alter
    27
    Beiträge
    587

    Inline Assembler - Variablenverwaltung / Warnungen

    Anzeige

    Hallo,

    ich will meinem Compiler die Registerauswahl überlassen, dazu habe ich eine Variable (hilf) definiert(uint8_t hilf) und weißer der dann im folgenden im InlineAssembler einen Wert zu. Die Zuweisung muss nähmlich GENAU da erfolgen.

    Mit der Zeit nerven aber die Warnungen(hilf is used uninzilized), wie kann ich dem Compiler sagen, dass ich die Warnungen nicht mehr sehen will, an der Stelle?
    Oder wie kann ich dem Compiler sagen, dass eine C Funktion genau an einer bestimmten Stelle ausgeführt werden soll? (Anmerkung: Der Compiler verschiebt die Variablenzuweisung immer und dann kommt Mist raus... So könnte man auch das Problem lösen.)

    Ich hoffe Ihr könnt mir helfen, das Wiki konnte es nämlich nicht.

    Grüße

    Michael

  2. #2
    Erfahrener Benutzer Robotik Einstein Avatar von SprinterSB
    Registriert seit
    09.06.2005
    Ort
    An der Saar
    Beiträge
    2.801
    Ohne deinen Code zu sehen und was du da treibst (oder versuchst zu treiben) ist schlecht Rat zu geben.

    Eine C-Funktion (bzw. Anweisung) wird irgendwann ausgeführt, und zwar so, daß die Abhängigkeiten der Variablen berücksichtigt werden.

    Evtl. fehlt irgendwo ein "volatile" wenn's auf die Reihenfolge ankommt, evtl muss ein Block/Funktionsaufruf atomar erfolgen.

    Die Warnung in Inline Assembler kommt wohl daher, daß du eine nichtinitialisierte Variable als Input-Operand verwendest.
    Disclaimer: none. Sue me.

  3. #3
    Erfahrener Benutzer Roboter-Spezialist
    Registriert seit
    08.07.2006
    Ort
    Karlsruhe/München
    Alter
    27
    Beiträge
    587
    Hallo mein Code:
    Code:
    #define edelay3(tacktschritte){ \
       int a=tacktschritte; \
       uint8_t b=tacktschritte%3; \
       {\
       a=a/3; \
       uint8_t register hilf; \
       asm volatile( \
       "ldi %1,%0\n" \
       "edelay3_%=:\n" \
       "dec %1\n" \
       "BRNE edelay3_%=\n" \
       : : "M" (a),"r" (hilf) ); \
       hilf=0; \
       }\
       if(b==0){ \
         asm(";"); \
       } \
       if(b==1){ \
         asm("NOP\n"); \
       } \
       if(b==2){ \
         asm("NOP\nNOP\n"); \
       } \
       if(b==3){ \
         asm("NOP\nNOP\nNOP\n"); \
       } \
    }
    Funktioniert eigentlich bis auf die Warnmeldung prächtig.
    Ich würde gerne schreiben hilf=a, das problem ist aber, es wird bei Schleifen manchmal verschoben, dass hilf nicht neu geladen wird.
    Voltaile schreibt das doch aber die Variable nur immer ins Ram?

    Ich hoffe Du kannst mir helfen.

    Der Main C Code:
    Code:
    #include <avr/io.h>
    #include <edelay.h>
    
    #define us_port PORTC
    #define us_ddr DDRC
    #define us_pin 0
    // #if F_CPU==1000000
    // #error "aa";
    // #endif
    void ultraschall_sendc(uint8_t burst){
      uint8_t i;
      us_ddr|=(1<<us_pin);
      i=burst;
    //hier wird hilf geladen
      do{
    //hier müsste hilf geladen werden
        us_port|=(1<<us_pin);
    //hier hilf modifiziert
        edelay(((F_CPU/1000000)*15)-5);
        us_port&=~(1<<us_pin);
        edelay(((F_CPU/1000000)*15)-8);
        i--;
      }while(i!=0);
      uint8_t l=20;
      while(l!=0){
        edelay(690);
        l=l--;
      }
      us_ddr&=~(1<<us_pin);
    }
    
    int main(void){
      while(1){
        ultraschall_sendc(20);
      }
      return 0;
    }
    Grüße

  4. #4
    Erfahrener Benutzer Roboter-Spezialist
    Registriert seit
    08.07.2006
    Ort
    Karlsruhe/München
    Alter
    27
    Beiträge
    587
    kann keiner mir helfen?

  5. #5
    Erfahrener Benutzer Robotik Einstein Avatar von SprinterSB
    Registriert seit
    09.06.2005
    Ort
    An der Saar
    Beiträge
    2.801
    Zunächst mal folgendes: Auch wenn der Code so erzeigt wird, wie es sein soll, gibt es keine Garantie dafür, daß dies immer so ist!
    elelay ist ja keine Funktion, sindern ein Makro, und so könnte zB b im Frame der Funktion angelegt werden, wenn die Funktion, die das Makro verwendet, komplex ist.

    Zudem ist es sehr ungünstig, /3 und %3 zu berechnen, weil das teuer ist. wesentlich besser wäre hier die Verwendung einer Schleife, die 4 Zyklen braucht!


    Code:
    #define NOP asm volatile ("nop")       
    				       
    #define edelay3 (taktschritte) 	       \
    do {				       \
    	uint16_t a = taktschritte / 4; \
    	uint8_t  b = taktschritte % 4; \
    				       \
    	asm volatile(		       \
    	   	"0:"		"\t"   \
    	   	"sbiw %0, 1" 	"\n\t" \
    		"brne 0b" 	"\n\t" \
    	   : "=w" (a)		       \
    	   : "0" (a)		       \
    	);			       \
       				       \
       if (b > 0) NOP;		       \
       if (b > 1) NOP;		       \
       if (b > 2) NOP;		       \
    } while(0)
    Das erste ist asm ist gerade die Warteschleife _delay_loop_2 (uint16_t) aus <util/delay.h>

    BTW: Anstatt rumzuwarten wäre für Ultraschall nicht besser ein Timer + PWM angebracht, falls frei?
    Disclaimer: none. Sue me.

  6. #6
    Erfahrener Benutzer Roboter-Spezialist
    Registriert seit
    08.07.2006
    Ort
    Karlsruhe/München
    Alter
    27
    Beiträge
    587
    Vielen Dank für Deine Hilfe.

    Ich werde es noch in die edelay einbauen.

    Btw: Grundsätzlich das Du recht mit dem Timer+PWM Methode, kein Thema, aber ich möchte ein 3-8 Port Multiplexer verwenden, sprich das man 7 Ultraschall Sensoren ansprechen kann. Und da geht es halt nicht mit PWM.

    Grüße und nochmal danke für Deine Hilfe.

Berechtigungen

  • Neue Themen erstellen: Nein
  • Themen beantworten: Nein
  • Anhänge hochladen: Nein
  • Beiträge bearbeiten: Nein
  •