Forum: Mikrocontroller und Digitale Elektronik Einzelnen Bits eines Bytes PINs zuweisen


von Johannes (menschenskind)


Lesenswert?

Hallo

Ich habe eine Variable, die bitweise immer um 1 erhöht werden soll, also 
so: 0000-->0001-->0010 usw.

Meine Variable ist als Char angelegt und 5 Bits dieser Variable möchte 
ich nun unterschiedliche Pins zuordnen.

Wie mach ich das am gescheitesten?
P.S. Ich programmiere in C.

Danke

von Karl H. (kbuchegg)


Lesenswert?

Johannes Hofmann wrote:

> Meine Variable ist als Char angelegt und 5 Bits dieser Variable möchte
> ich nun unterschiedliche Pins zuordnen.

Wie ist die Zuordnungsvorschrift?

>
> Wie mach ich das am gescheitesten?

Am gescheitesten machst du das, in dem du die Hardware so herrichtest, 
dass du eine schöne Zurdnungsvorschrift hast: Die 5 Bits tauchen in der 
selben Reihenfolge nebeneinanderliegend an einem Port auf.

Dann ist das trivial.

In allen anderen Fällen kann das schon aufwendig werden, je nachdem wie 
die Bits auf unter Umständen mehrere Ports verteilt sind.

von Sumynona (Gast)


Lesenswert?

1
//Einfache Lösung des Problems. Geht natürlich sicher besser ;-)
2
3
#define MYBIT0 0
4
#define MYBIT1 1
5
#define MYBIT2 2
6
#define MYBIT1 3
7
#define MYBIT2 4
8
9
#define MYPORT PORTB
10
#define MYPIN0 PB3
11
#define MYPIN1 PB1
12
#define MYPIN2 PB7
13
#define MYPIN1 PB5
14
#define MYPIN2 PB4
15
16
void updateport(unsigned char value)
17
{
18
    if(value & (1 << MYBIT0)) { MYPORT |= (1 << MYPIN0); } else { MYPORT &= ~(1 << MYPIN0); }
19
    if(value & (1 << MYBIT1)) { MYPORT |= (1 << MYPIN1); } else { MYPORT &= ~(1 << MYPIN1); }
20
    if(value & (1 << MYBIT2)) { MYPORT |= (1 << MYPIN2); } else { MYPORT &= ~(1 << MYPIN2); }
21
    if(value & (1 << MYBIT3)) { MYPORT |= (1 << MYPIN3); } else { MYPORT &= ~(1 << MYPIN3); }
22
    if(value & (1 << MYBIT4)) { MYPORT |= (1 << MYPIN4); } else { MYPORT &= ~(1 << MYPIN4); }
23
}

von Sumynona (Gast)


Lesenswert?

ups, copy & paste hat mich erwischt... es muss natürlich MYBIT3 und 
MYBIT4 sowie MYPIN3 und MYPIN4 heißen, bei den definitionen

von Peter D. (peda)


Lesenswert?


von Johannes (menschenskind)


Lesenswert?

Hallo,

Zuordnungsvorschrift in diesem Sinn?

   unsigned char Pixel_Cell;

    for(i=0;i<16;i++){

      Pixel_Cell += 0x01;
    }

Wie gesagt, ein Binärzähler. Und die einzelnen Bits muss ich dort 
rausziehen.

von Justus S. (jussa)


Lesenswert?

Johannes Hofmann wrote:

> Zuordnungsvorschrift in diesem Sinn?

nein, welches Bit zu welchem Pin an welchem Port...

von Johannes (menschenskind)


Lesenswert?

Bit 0 soll an Pin 1.0
...
Bit 5 soll an Pin 1.4

Leider konnte ich noch kein Zuordnungs-Datei für die einzelnen Pins 
finden.
Beim AVR geht das ja schön mit PB0, PB1, usw.

Doch wie läuft das beim MSP? P1.0, P1.1,...?

von Karl H. (kbuchegg)


Lesenswert?

Johannes Hofmann wrote:
> Bit 0 soll an Pin 1.0
> ...
> Bit 5 soll an Pin 1.4
>
> Leider konnte ich noch kein Zuordnungs-Datei für die einzelnen Pins
> finden.
> Beim AVR geht das ja schön mit PB0, PB1, usw.
>
> Doch wie läuft das beim MSP? P1.0, P1.1,...?

Ich bin mir ziemlich sicher, dass man auch auf dem MSP-Compiler mit 
Standard C-Mitteln durch

   P1 |= ( 1 << 0 );

das Bit Nr 0 am Port P1 setzen kann. Kein Mensch zwingt dich, das über 
einen Zugriff über P1.0 zu erledigen.

von Johannes (menschenskind)


Lesenswert?

Ja so funktioniert es auch, aber bei meinem Fall ist es so, dass ich 
Daten an einen 5-zu-32-Decoder schicke.
Und dieser benötigt die Daten auf einen Schlag. Nach der Variante von 
Sumynona würde der Port1 die Daten aber hintereinander bekommen.
Ich muss das also so machen, dass P1.0 bis P1.4 die Daten von meiner 
Ausgangsvariable alle zur selben Zeit bekommen.

Wie könnte ich das machen?

von Karl H. (kbuchegg)


Lesenswert?

Johannes Hofmann wrote:
> Ja so funktioniert es auch, aber bei meinem Fall ist es so, dass ich
> Daten an einen 5-zu-32-Decoder schicke.
> Und dieser benötigt die Daten auf einen Schlag. Nach der Variante von
> Sumynona würde der Port1 die Daten aber hintereinander bekommen.
> Ich muss das also so machen, dass P1.0 bis P1.4 die Daten von meiner
> Ausgangsvariable alle zur selben Zeit bekommen.
>
> Wie könnte ich das machen?

Indem du nur eine Zuweisung an P1 machst?

  P1 |= ( 1 << 0 ) | ( 1 << 4 ) | ( 1 << 6 );

setzt gleichzeitig Bit 0, Bit 4 und Bit 6 am Port P1 auf 1.

Zur Not kann man sich ja auch noch das auszugebende Bitmuster zuvor in 
einer Variablen zurechtlegen und diese dann auf einen Schlag ausgeben.


   unsigned char Muster = 0;

   if( Counter & 0x01 )
     Muster |= 1 << 0;

   if( Counter & 0x02 )
     Muster |= 1 << 4;

   if( Counter & 0x03 )
     Muster |= 1 << 6;

   P1 = Muster;


gibt die untersten 3 Bits des Counters auf den Pins 0, 4 und 6 in einem 
Schlag aus.

von PJ (Gast)


Lesenswert?

Ich weiß ja nicht, was Du mit den Dekoderausgängen steuern willst, aber 
die sauberste Methode wäre wahrscheinlich nicht einfach "auf einen 
Schlag ausgeben", sondern "1. den 5-Bit-Dekoderwert ausgeben und 2. den 
Enable- oder Latch-Pin umschalten". Wer weiß, was Du sonst womöglich für 
Störimpulse auslöst.

von Peter D. (peda)


Lesenswert?

Johannes Hofmann wrote:
> Ja so funktioniert es auch, aber bei meinem Fall ist es so, dass ich
> Daten an einen 5-zu-32-Decoder schicke.
> Und dieser benötigt die Daten auf einen Schlag. Nach der Variante von
> Sumynona würde der Port1 die Daten aber hintereinander bekommen.

Gleichzeitig geht eh nichts, schon die 1-0 und 0-1 Übergänge haben 
unterschiedliche Zeiten. Es ist also nicht garantiert, daß nicht 
kurzzeitig andere Dekoderausgänge pulsen.
Um das zu verhindern, mußt Du den Enable-Pin des Dekoders benutzen, also 
disable, Bitmuster ändern, enable.


Peter

von Johannes (menschenskind)


Lesenswert?

Das lustige ist ja, dass der Decoder keinen Enable-Eingang hat.
Sondern nur die 5 Eingänge für den Vektor.

von Karl H. (kbuchegg)


Lesenswert?

Grade erst gesehen.

Bei ...
> Bit 0 soll an Pin 1.0
> ...
> Bit 5 soll an Pin 1.4

(Ich geh mal davon aus, dass Bit 5 ein Schreibfehler ist)

würde sich natürlich anbieten

  P1 = ( P1 & 0xE0 ) | ( Count & 0x1F );

oder wie dann auch immer der lesende Zugriff auf P1 geht. Entscheidend 
ist nur: P1 lesen, die unteren 5 Bits auf 0 setzen, vom Counter die 
unteren 5 1-Bits übernehmen, auf P1 schreiben. Wenn der Zustand der 
restlichen 3 Bits an P1 egal ist, dann natürlich

   P1 = Counter;

Oder auch Kombinationen davon:
die untersten 3 Bits gemeinschaftlich über & und | Maskierungen, und nur 
1 Bit wird spezielabbehandelt, weil in der Pinbelegung ein Loch ist, 
oder ...
Nicht zu vergessen auch die Möglichkeiten, mal mit einem Schiebebefehl 
in "Bit-Loch" in ein Byte zu schlagen, ...

Auch über ein Umkodierarray könnte man nachdenken: Der Counterwert ist 
Index in das Array und aus dem Array kriegt man den Wert, den man 
ausgeben muss. Dieser Wert ist so konstruiert, dass die richtigen Pins 
entsprechend des Counters angesteuert werden.

Möglichkeiten gibts viele. Hängt alles davon ab, wie deine Bit zu Pin 
Zuordnung konkret aussieht. Und genau deshalb hab ich dich ganz am 
Anfang nach dieser Zurdnungsvorschrift gefragt.

Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.