SDCC generiert ungültige Programme für PIC 16f628a

Ich habe gelernt, wie man für PIC 16f628A codiert, und ich habe einen sehr einfachen Code geschrieben, um eine LED einzuschalten, die mit RB0 verbunden ist, und sie eingeschaltet zu lassen. Meine ursprüngliche Absicht war, SDCC und GPUTILS zu verwenden, um die Projekte zu kompilieren. Es scheint jedoch, dass SDCC oder GPUTILS ungültige Hex-Dateien erzeugen, da das Programm nicht wie erwartet funktioniert, wenn ich es auf den Chip hochlade, bleibt die LED während der gesamten Programmausführung aus. Ein ähnlicher Code, der mit dem Compiler von CSC kompiliert wurde, läuft ohne Probleme. Außerdem hatte ich keinen Erfolg beim Ausführen eines einfachen Programms, das mit GPASM kompiliert wurde. Es ist bemerkenswert, dass GPSIM all diese Programme perfekt ausführt und zeigt, dass die Pins wie erwartet funktionieren. Ich benutze K150 als Programmierer. Ich weiß nicht, was mit SDCC und GPUTILS los ist.

#include "pic16f628a.h"
//#include "tsmtypes.h"
//#include "tsmpic.h"

#include <stdint.h>

//CONFIG:__config (_CP_OFF & _LVP_OFF & _BOREN_OFF & _MCLRE_ON & _WDT_OFF & _PWRTE_ON & _INTOSC_OSC_NOCLKOUT)

uint16_t __at 0x2007  __CONFIG = _CP_OFF & _LVP_OFF & _BOREN_OFF & _MCLRE_ON & _WDT_OFF & _PWRTE_ON & _INTOSC_OSC_NOCLKOUT;

#define CLOCK_8MHZ 0
#define CLOCK_4MHZ 1

void main(void)
{
    //SCS = 1;

    TRISA = 0x00;
    TRISB = 0x00;

#ifdef __16f628a    // Only compile this section for PIC16f628a
    CMCON = 0x07;   /** Disable comparators.  NEEDED FOR NORMAL PORTA
         *  BEHAVIOR ON PIC16f628a!          */
#endif

    // Loop forever.  
    while(1) {
        RB0 = 1;
    }
}
Ich verwende die interne Uhr
Welche SDCC-Version? Ich glaube, die PIC-Unterstützung war eine Zeit lang "in der Beta", haben sie jemals das PIC-Ziel für die Veröffentlichung fertiggestellt?
Die Version, die ich verwende, ist 3.3. Ich dachte, die Unterstützung der SDCC für PIC sei besser als das.

Antworten (2)

Was ist die physische Konfiguration Ihres MCLR-Pins? In Ihrer Konfiguration ist MCLR aktiviert. Wenn Sie also VCC nicht an den MCLR-Pin (Pin4 / RA5) liefern, halten Sie im Grunde die Reset-Taste gedrückt.

Ändern Sie Ihre Konfigurationsanweisung in:

uint16_t __at 0x2007  __CONFIG = _CP_OFF & _LVP_OFF & _BOREN_OFF & _MCLRE_OFF & _WDT_OFF & _PWRTE_ON & _INTOSC_OSC_NOCLKOUT;

Generell fand ich es nützlich, alle Konfigurationsoptionen, die ich nicht verwende, explizit zu deaktivieren. Es verhindert Dinge wie von MCLR gebissen zu werden, aber es zwingt mich auch, mehr vom Datenblatt zu lesen und mehr über die Funktionen des Mikrocontrollers zu erfahren.

Ich sehe auch aus Ihrem Kommentar, dass Sie SDCC 3.3 verwenden. Ab diesem Beitrag ist SDCC 3.5.5 verfügbar. Das aktuelle SDCC-Handbuch empfiehlt die Verwendung von #pragma config zum Setzen von Konfigurationsbits, da die in Ihrem Beispiel verwendete Methode veraltet ist. Hier ein Auszug aus dem Handbuch:

4.6.17 Configuration Bits
Configuration bits (also known as fuses) can be configured using one of two methods:

• using #pragma config (see section 4.6.6), which is a preferred method for the new code. Example:

#pragma config CP0=OFF,OSCS=ON,OSC=LP,BOR=ON,BORV=25,WDT=ON,WDTPS=128,CCP2MUX=ON
#pragma config STVR=ON

• using ‘__code’ and ‘__at’ modifiers. This method is deprecated. Possible options should be ANDed and
can be found in your processor header file. Example for PIC18F2550:

#include <pic18fregs.h> //Contains config addresses and options
static __code char __at(__CONFIG1L) configword1l =
_USBPLL_CLOCK_SRC_FROM_96MHZ_PLL_2_1L &
_PLLDIV_NO_DIVIDE__4MHZ_INPUT__1L & [...];
static __code char __at(__CONFIG1H) configword1h = [...];
static __code char __at(__CONFIG2L) configword2l = [...];
//More configuration words

Mixing both methods is not allowed and throws an error message ”mixing __CONFIG and CONFIG directives”.

Wenn Sie also die im SDCC-Handbuch empfohlene Methode verwenden, wäre Ihr Konfigurationsblock:

/* CONFIGURATION Bits */
#pragma config CP=OFF,CPD=OFF,LVP=OFF,BOREN=OFF
#pragma config MCLRE=OFF,PWRTE=OFF,WDTE=OFF
#pragma config FOSC=INTOSCIO    

Ich habe festgestellt, dass WatchDog Timer mit pic16f628 und pic16f628A nicht deaktiviert ist, wenn Sie OSC und ClockOut wählen. Ich weiß nicht, ob SDCC oder gpasm schuld ist.

BEARBEITEN

Der Fehler befindet sich in der Header-Datei /usr/share/gputils/header/p16f628a.inc, der Wert für WDTE_OFF 0x3ff7 ist falsch und deaktiviert das WDT nicht für alle Konfigurationen, sondern wirkt sich auf die Uhrenkonfiguration aus. Der richtige Wert ist 0x3ffb. Und die Datei p16f628.inc hat den falschen Wert.

Die obige Antwort mit Pragma-Sache ist für die 18f-Familie nicht die alte 16f628.