Hey, ich wollte mit meinem MSP Schieberegister ansteuern. Zuerst habe ich eine minimale Schaltung aufgebaut ohne Last, um zu überprüfen, ob die Ausgänge funktionieren(siehe Anhang). Mein CLK und mein OE funktionieren wunderbar. Auf den anderen Ports Latch und SIMO passiert nichts. Ich kann mir das nicht erklären und wäre für eine Hilfe dankbar.
Sry nochmal. Mein Code:
1 | #include "msp430g2553.h" |
2 | |
3 | |
4 | |
5 | void delay(unsigned int i); |
6 | void enable(void); |
7 | void disable(void); |
8 | void latch_on(void); |
9 | void latch_off(void); |
10 | void write_SPI(unsigned long long data); |
11 | |
12 | |
13 | volatile unsigned long long Data; //64 bit |
14 | int i, k; |
15 | |
16 | int main(void) |
17 | {
|
18 | |
19 | //int i;
|
20 | WDTCTL = WDTPW + WDTHOLD; // Stop watchdog timer |
21 | BCSCTL1 = CALBC1_1MHZ; //changing the DCO's oscillations to 16MHz |
22 | DCOCTL = CALDCO_1MHZ; |
23 | |
24 | //P2SEL =0;
|
25 | //P1SEL =0;
|
26 | |
27 | P2DIR |= 0xC6; |
28 | P1DIR |= 0x14; |
29 | P1SEL |= 0x14; |
30 | P2SEL &= ~0xC0; |
31 | //P3SEL |= 0x31;
|
32 | UCA0CTL1 |= UCSWRST; // RESET |
33 | UCA0CTL0 |= UCCKPH + UCMSB + UCMST + UCSYNC; |
34 | UCA0CTL1 |= UCSSEL_2; |
35 | UCA0BR0 = 0x00; |
36 | UCA0BR1 = 0; |
37 | UCA0MCTL = 0; |
38 | UCA0CTL1 &= ~UCSWRST; |
39 | |
40 | //printf("Hallo Welt\n");
|
41 | |
42 | Data=0x11D521084; |
43 | while(1) |
44 | {
|
45 | if (Data==0x8EA908420000) |
46 | {
|
47 | Data=0x11D521084; |
48 | k=0; |
49 | }
|
50 | |
51 | if(k==1) |
52 | {
|
53 | Data=Data<<5; // Increment Data value |
54 | }
|
55 | write_SPI(Data); |
56 | latch_on(); |
57 | enable(); |
58 | delay(500); |
59 | disable(); |
60 | k=1; |
61 | }
|
62 | }
|
63 | |
64 | // Fubnktion Daten in den Shiftregister schieben
|
65 | |
66 | void write_SPI(unsigned long long data) |
67 | {
|
68 | latch_off(); |
69 | while (!(IFG2 & UCA0TXIFG)); // USCI_A0 TX buffer ready? |
70 | UCA0TXBUF = data>>56; // Byte to SPI TXBUF |
71 | while (!(IFG2 & UCA0TXIFG)); // USCI_A0 TX buffer ready? |
72 | UCA0TXBUF = data>>48; // Byte to SPI TXBUF |
73 | while (!(IFG2 & UCA0TXIFG)); // USCI_A0 TX buffer ready? |
74 | UCA0TXBUF = data>>40; // Byte to SPI TXBUF |
75 | while (!(IFG2 & UCA0TXIFG)); // USCI_A0 TX buffer ready? |
76 | UCA0TXBUF = data>>32; // Byte to SPI TXBUF |
77 | while (!(IFG2 & UCA0TXIFG)); // USCI_A0 TX buffer ready? |
78 | UCA0TXBUF = data>>24; // Byte to SPI TXBUF |
79 | while (!(IFG2 & UCA0TXIFG)); // USCI_A0 TX buffer ready? |
80 | UCA0TXBUF = data>>16; // Byte to SPI TXBUF |
81 | while (!(IFG2 & UCA0TXIFG)); // USCI_A0 TX buffer ready? |
82 | UCA0TXBUF = data>>8; // Byte to SPI TXBUF |
83 | while (!(IFG2 & UCA0TXIFG)); // USCI_A0 TX buffer ready? |
84 | UCA0TXBUF = data; // Byte to SPI TXBUF |
85 | while (!(IFG2 & UCA0TXIFG)); // USCI_A0 TX buffer ready? |
86 | //delay(100); // Delay
|
87 | }
|
88 | |
89 | void latch_on( void ) |
90 | {
|
91 | P2OUT |= 0x4; |
92 | P2OUT &= ~0x4; |
93 | |
94 | }
|
95 | |
96 | void latch_off(void) |
97 | {
|
98 | P2OUT &= ~0x4; |
99 | }
|
100 | |
101 | void delay(unsigned int ms) |
102 | {
|
103 | while (ms--) |
104 | {
|
105 | __delay_cycles(1000); |
106 | }
|
107 | }
|
108 | |
109 | void enable( void ) |
110 | {
|
111 | P2OUT &= ~0x2; |
112 | }
|
113 | |
114 | void disable( void ) |
115 | {
|
116 | P2OUT |= 0x2; |
117 | }
|
Steffen M. schrieb: > P1SEL |= 0x14; > P2SEL &= ~0xC0; Hast Du Dir im "Family User's Guide" mal angesehen, wie diese beiden Register nach dem POR initialisiert sind? Hältst Du das hier > P2SEL &= ~0xC0; tatsächlich für lesbarer als das hier? > P2SEL &= 0x3F; Und warum verwendest Du hier hexadezimale Konstanten, statt die in den Headerfiles für die einzelnen Bits definierten #defines zu nutzen? Und ist Dir aufgefallen, daß die Funktion "latch_on" das Bit setzt, um es sofort danach wieder zu löschen? Wozu dient dann die Funktion "latch_off"?
Rufus, deine Gegenfragen sind nich hilfreich. > Hältst Du das hier > P2SEL &= ~0xC0; > tatsächlich für lesbarer als das hier? > P2SEL &= 0x3F; Ja, ich schon. > Und ist Dir aufgefallen, daß die Funktion "latch_on" das Bit setzt, > um es sofort danach wieder zu löschen? Na und, genau dieses Verhalten ist wohl gewollt. Ich nehem an, dadurch soll das Takt-Signal für das Schieberegister erzeugt werden. Was ist daran falsch? Ich würde eher den irreführenden Namen der Funktion kritisieren. > Wozu dient dann die Funktion "latch_off"? Offensichtlich ein ungenutzter Überrest aus Zeiten, als die latch_on Funktion noch das tata, was ihr Name suggeriert.
stefanus schrieb: > Rufus, deine Gegenfragen sind nich hilfreich. Ach. Hast Du Dich auch mit den anderen Gegenfragen beschäftigt, oder findest Du generell Gegenfragen "nich hilfreich", weil Du erwartest, alles auf silbernen Tabletts serviert zu bekommen?
So, das Problem habe ich gelöst. Der Blick ins Blockschaltbilder hat mein Fehler aufgezeigt. Bei mir habe ich nur P1SEL gemaacht. Dadurch wird aber nur der Timer durchgeschoben. Man musste auch P2SEL für USCI benutzen:
1 | // [...]
|
2 | BCSCTL2 = 0; |
3 | |
4 | P2SEL =0; |
5 | P2SEL2 =0; |
6 | P1SEL =0; |
7 | P1SEL2 =0; |
8 | |
9 | P1DIR =0; |
10 | P2DIR =0; |
11 | |
12 | P1DIR |= BIT2 + BIT4; |
13 | P2DIR |= BIT1 + BIT2; |
14 | |
15 | P1SEL |= BIT2 + BIT4; |
16 | P1SEL2 |= BIT2 + BIT4; |
17 | |
18 | //P2DIR |= 0xCA;
|
19 | //P1DIR |= 0x14;
|
20 | //P1SEL |= 0x14;
|
21 | //P2SEL &= ~0xC0;
|
22 | //P3SEL |= 0x31;
|
23 | UCA0CTL1 |= UCSWRST; // RESET |
24 | [...]
|
latch_off ist tasächlich aus früheren Zeiten. Ich glaube die Idee war um ein LOW auf dem Latch Port sicherzustellen vor dem Schieben der Daten(MOSI).
Na also. Siehst Du, meine Gegenfragen haben doch etwas gebracht -- Du hast offensichtlich in den "Family User's Guide" gesehen. Genau das war (unter anderem) die Intention.
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
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.