PIC16F628A + USART + HC05 = nope

PIC, AVR, Arduino, Raspberry Pi, Basic Stamp, PLC mm.
bos
Inlägg: 2275
Blev medlem: 24 februari 2007, 23:29:15
Kontakt:

PIC16F628A + USART + HC05 = nope

Inlägg av bos »

Jag har köpt två Bluetooth-moduler (HC-05) på ett breakout-board för att testa lite. Jag har kört AT-läget på båda moduler för att ställa in dem enligt följande:

Kod: Markera allt

master:

AT+UART=115200,0,0
AT+ROLE=1
AT+CMODE=0
AT+BIND=aaaa,bb,cccccc (slave-addr)

slave:

AT+UART=115200,0,0
AT+ROLE=0
AT+CMODE=0
AT+BIND=aaaa,bb,cccccc (master-addr)
Testade sen att koppla upp dem båda mot var sin USB-TTL-adapter för att se om de kunde kommunicera, och det var inga problem. Det jag skrev i minicom för mastern dök upp på minicom för slaven.

Men sen blev det lite lurigare. Jag byggde två prototypkort på veroboard. I princip identiska byggen, med enda skillnaden att RB0 är jordad på slaven så att jag i firmwaren (samma till båda) kan känna av om det är master eller slave som koden ska köras för. Korten har en 20MHz-kristall och fungerar (testkört båda med blinkande LED). Jag sätter sen upp USART-modulen att köra i 115kbaud, men sen är det tvärstopp. Jag får inte kommunikationen att fungera.

Här är min testkod:

Kod: Markera allt

#include <xc.h>

bit is_master;

// CONFIG
#pragma config FOSC = HS
#pragma config WDTE = OFF
#pragma config PWRTE = ON
#pragma config MCLRE = ON
#pragma config BOREN = OFF
#pragma config LVP = OFF
#pragma config CPD = OFF
#pragma config CP = OFF

void init_uart() {
    TXSTA = RCSTA = 0;

    if (is_master) {
        // Async RS232
        SYNC = 0;               // asynchronous
        SPEN = 1;               // enable serial port
        TXIE = 0;               // no USART-interrupts
        TXEN = 1;               // enable transmitter
        BRGH = 1;               // use high baud rate
        SPBRG = 10;             // 115200 baud @ 20 MHz  (page 78)
    } else {
        SYNC = 0;
        SPEN = 1;
        RCIE = 0;
        CREN = 1;
        BRGH = 1;
        SPBRG = 10;
   }
}

void send_device_state(char data) {
    while(!TXIF)
        continue;
    TXREG = data;
}

void init_MCU() {
    // If RB0 is connected to ground, device is in slave-mode.
    // Therefore, check this bit prior everything else.
    TRISB = 0b00000001;     // RB0 - input

    is_master = RB0;
    if (is_master) {
        TRISA = -1;         // All inputs
        TRISB = -1;         // All inputs
    } else {
        TRISA = 0b11100000; // RA0-4 outputs
        TRISB = 0b00000000; // All outputs
        PORTA = -1;         // Raise all pins (= device idle)
    }

    OPTION_REG = 0;         // Enable WPU on RB

    // Interrupts
    INTCON = 0;
}

void main() {
    init_MCU();
    init_uart();

    while (1) {
      send_device_state('T');
      send_device_state('e');
      send_device_state('s');
      send_device_state('t');
    }
}
Jag programmerar mastern med HC-05 ditkopplad, och sätter slav-HC-05:an på min USB-adapter och ställer in minicom till 115200 8N1 (precis som förut). Mitt väntade resultat här är att se strängen "Test" skriven på skärmen i all oändlighet, men jag ser ingenting. HC-05 och PIC är kopplad RX<->TX och tvärtom.

När det kört kanske en minut ploppar det upp ett "L" på skärmen, men inget mer.

Med hjälp av lite LED-debugging fann jag att koden stannar i while-loopen inne i send_device_state(). Har försökt hitta tips i databladet, men jag hittar ingen lösning. Nu efter 4-5 timmar har jag inte längre något mer att testa med, och har heller inga fler idéer.

Det enda jag inte har testat är att sätta en spänningsdelare på RX. Detta för att enligt databladet till min modul ska RX/TX vara 5V-säkra trots att det står 3.3V på dem.

Så; kan detta problem härröra sig ur att det är 5V, eller har jag missat något i koden? Eller något annat?
Användarvisningsbild
hanpa
Utsparkad, på semester
Inlägg: 639
Blev medlem: 22 november 2016, 21:54:43
Ort: Hemort

Re: PIC16F628A + USART + HC05 = nope

Inlägg av hanpa »

Jag kan inte plattformen men behövs ingen delay i loopen ifall man ska hinna köra något annat administrativt? Annars käkas ju all tid upp på busy wait. Men jag vet som sagt inte hur plattformen fungerar.
Användarvisningsbild
lillahuset
Gått bort
Inlägg: 13969
Blev medlem: 3 juli 2008, 08:13:14
Ort: Norrköping

Re: PIC16F628A + USART + HC05 = nope

Inlägg av lillahuset »

Kolla villkoret för att TXIF ska sättas hög.
Det känns som jag har varit med om samma problem med PIC för ett par decennier sedan. Har ett vagt minne av att TXIF sattes bara när ett tecken hade skickats. Finns det någon annan flagga förknippad med TXREG?
Fast det kan ha varit någon annan processor än PIC förståss.

Kollade databladet: Det är TRMT du ska använda.
bos
Inlägg: 2275
Blev medlem: 24 februari 2007, 23:29:15
Kontakt:

Re: PIC16F628A + USART + HC05 = nope

Inlägg av bos »

http://www.microchip.com/forums/m/tm.aspx?m=608851&p=1 säger i princip samma som databladet:
If TXIF is set, you can write to TXREG. That's all you need to know unless you have an unusual application. Ignore TRMT.
Användarvisningsbild
lillahuset
Gått bort
Inlägg: 13969
Blev medlem: 3 juli 2008, 08:13:14
Ort: Norrköping

Re: PIC16F628A + USART + HC05 = nope

Inlägg av lillahuset »

Nja, läs 12.2.1 i DS40044G-page 79.

Använder du interrupt så använd gärna TXIF men den kommer inte att sättas förrän en byte har lämnat USARTen.

Edit: Kolla FIGURE 12-2: ASYNCHRONOUS TRANSMISSION
bos
Inlägg: 2275
Blev medlem: 24 februari 2007, 23:29:15
Kontakt:

Re: PIC16F628A + USART + HC05 = nope

Inlägg av bos »

Nu har jag testat lite mer. Det blir ingen skillnad om jag pollar TRMT istället, men enligt forumtrådar blir det race condition om pollen samt TXREG-tilldelningen sker instruktionsmässigt sett efter varandra. Därför lade jag in en liten delay.

Om jag kör 8 nop så får jag text på skärmen. Texten är dock inte "Test", utan "&L&L&L&L&L&L&L ...". Någon sorts framsteg, antar jag.

Sen gjorde jag ett test med en delay-funktion:

Kod: Markera allt

void delay(void) {
    for (unsigned int n = 0; n < 1145; n++) {
        volatile unsigned int l;
        l = n;
    }
}
och anropar, då blir texten "tetetetete ...", dvs "T" och "s" hoppas över. Samma resultat om delay är före eller efter while.

Jag provade då att skriva ut en större sträng, "ABCDEFGHIJKLMNOPQRSTUVWXYZ".

Resultat: "ABDGHKMNPSUVYZ". Exakt dessa bokstäver i exakt den följden. Alla andra hoppas över. Verkade ju lite märkligt, så jag ändrade strängen till "CBCDEF...". Resultat: "BDGHK...".

Med andra ord; bokstaven "C" kan inte skickas alls. :shock:


Vad felar här, tro? :humm:
Användarvisningsbild
hanpa
Utsparkad, på semester
Inlägg: 639
Blev medlem: 22 november 2016, 21:54:43
Ort: Hemort

Re: PIC16F628A + USART + HC05 = nope

Inlägg av hanpa »

Din delay är ännu en busy wait. FInns det ingen inbyggd delay/yield-funktion som i Arduino IDE:n? Så att annat som behöver köras får CPU-tid?
bos
Inlägg: 2275
Blev medlem: 24 februari 2007, 23:29:15
Kontakt:

Re: PIC16F628A + USART + HC05 = nope

Inlägg av bos »

Jag har ingenting annat som behöver köras. Denna controllers enda uppgift är att läsa av status på 10 GPIO och sen spotta ut resultatet på USART.
Användarvisningsbild
Jan Almqvist
Inlägg: 1581
Blev medlem: 1 oktober 2013, 20:48:26
Ort: Orust

Re: PIC16F628A + USART + HC05 = nope

Inlägg av Jan Almqvist »

Paritetsfel?

A (0x41) och B (0x42) har lika många ettor, C (0x43) har en etta mer.
Användarvisningsbild
hanpa
Utsparkad, på semester
Inlägg: 639
Blev medlem: 22 november 2016, 21:54:43
Ort: Hemort

Re: PIC16F628A + USART + HC05 = nope

Inlägg av hanpa »

OK, ja då borde det ju vara lugnt...
bos
Inlägg: 2275
Blev medlem: 24 februari 2007, 23:29:15
Kontakt:

Re: PIC16F628A + USART + HC05 = nope

Inlägg av bos »

Jan Almqvist skrev:Paritetsfel?

A (0x41) och B (0x42) har lika många ettor, C (0x43) har en etta mer.
Det verkar stämma. Alla de tecken som försvinner har tre ettor i sig, så om jag vågar gissa lite friskt är det data med udda antal ettor som blir skrot.
bos
Inlägg: 2275
Blev medlem: 24 februari 2007, 23:29:15
Kontakt:

Re: PIC16F628A + USART + HC05 = nope

Inlägg av bos »

Paritetsproblemet löst: av misstag hade jag råkat sätta en av mina BT-moduler att köra med paritet, medan den andra körde utan.

Efter att ha configgat om båda till att köra utan så ramlar inga tecken bort i överföringen.
Skriv svar