Hot answers tagged

22

The problem is not with your type but with the way you print it. In C %d format specifier is for int, not for long. For signed long you should use %ld instead, if your compiler supports it. For unsigned use %lu.


20

This is to specify an absolute address to place the variable at. From the XC8 compiler manual page 27, section 2.5.2 Absolute Addressing: Variables and functions can be placed at an absolute address by using the __at() construct ...... 2.5.2.2 DIFFERENCES The 8-bit compilers have used an @ symbol to specify an absolute address


14

Since you wrote your own answer, it's clear that you wanted to promote a particular solution. In a more general sense, the standard C regex library is for both compiling and executing regular expressions, and relies on services provided by a POSIX-compliant operating system. Compiling is much more complicated (it involves first parsing the regular ...


11

64-bit datatypes are available to use but you must use the following flags when compiling: --std=C99 --ext=cci This makes the compiler use the C99 standard with the Common C Interface. With these compiler flags you will be able to use 64-bit integers. However, it may require you to reformat your code as some C90 code will not play nicely with C99. It is ...


7

Have you read the XC8 user's guide? Section 5.9 deals with interrupts. In there it states: The function qualifier interrupt (or __interrupt) can be applied to a C function definition so that it will be executed once the interrupt occurs. The compiler will process the interrupt function differently to any other functions, generating code to save and ...


7

In C it is best practice to use prototypes. Generally, you want to declare your function prototypes in a header file. For your code perhaps call the header file BCD.h and create it in the 'Header Files' section of MPLAB. The header file code should look something like the following: #ifndef BCD_H #define BCD_H uint8_t updateBCD(uint8_t); #endif then ...


7

It's right there in the user guide in black and white... bit and __bit are exactly the same, except for the level of compatibility: If the xc8 flag --STRICT is used, the bit keyword becomes unavailable, but you can use the __bit keyword. So you can use bit for your own data type, variable name, function name, whatever you want, if you specify --STRICT ...


6

You have a couple of issues with your code and circuit. A while loop with a false condition will never loop. Do you mean to put "while(0)" or is that a typo? Either way, that loop is never looping. Change the 0 to a 1. The PIC16F628A has a PGM pin that it uses in LVP (Low Voltage Programming) mode. It shares the same pin as RB4. The PGM pin must be tied to ...


6

There is no substitute for understanding the machine at the low level. Whether using a compiler or not, you have to actually READ THE DATASHEET. As Figure 2-3 on page 13 clearly shows, there is no way to get 256 contiguous bytes of RAM. Other observations: MPLABX is the IDE, so is useless in specifying what compiler or assembler you are using. ...


6

@ is a common non-standard extension to the C language which allows you to declare a variable at a specific address. It can be used for memory-mapped hardware registers etc. In which case the variable must also be declared volatile, so your example is incorrect. Other compilers use something like __attribute__(section... or #pragma ..., all of it non-...


5

One thing that would help (and is definitely best practise) would be to check what is causing the interrupt. You should also be writing to the latch (LATx register) on an 18F and you need to disable analogue functions. Sample code for this might look like: #define LED_OUTPUT LATC3 void main(void) { // .. other setup here .. // Disable analogue ...


5

From the XC8 C Compiler Users Guide, page 229:- 5.14.3 Predefined Macros __DATE__ to indicate the current date eg. May 21, 2004 __TIME__ to indicate the current time eg. 08:06:31 You can parse these strings to get numbers compatible with your rtc, but what's the point of a real time clock that doesn't have the real time? Anyway, look at this Stack ...


5

I have solved my question. The problem is that I was using the 1.40 version of XC8 compiler. The periperial libraries are not longer supported and were compiled with version 1.34 of MPLAB XC8. Any changes made to header files since those libraries were created could potentially create a declaration mismatch. What I did was download the former 1.34 ...


5

Although it could be possible to get the library to compile with xc8, I had better luck using re2c, which is a utility that uses special syntax in your source file to produce a FSM that runs a regex. An example from their website: static int lex(const char *YYCURSOR) // YYCURSOR is defined as a function parameter { // ...


4

This is probably more of a general programming question than an electronics question, but since this group encompasses embedded systems programming to some extent, I'll answer it here. The C standard promises that code may use any syntactically-valid identifier without risk of conflict with any implementation-defined identifiers, provided that: The user ...


4

IIRC, most C compilers have a limit of 255 characters for an identifier. You usually find all the information you need in the compiler's manual. In your case it's the MPLAB XC8 C Compiler User’s Guide: 3.4.4.3 HOW LONG CAN I MAKE MY VARIABLE AND MACRO NAMES? The C Standard indicates that a only a specific number of initial characters in an identifier ...


4

Apart from missing the end bracket (copy/paste missed the last character?) your code works for me. However there are a couple of omissions that might make you think it doesn't:- #define _XTAL_FREQ 8000000 tells the compiler what frequency the PIC should be running at, but does not actually set it. On start up the 12F683 runs at 4MHz. To change it to 8MHz ...


4

If you can use C standard library functions, sprintf() should handle the string conversion. Instead of adding the decimal point by shuffling characters around, you could use integer arithmetic: char str[20]; unsigned int value = 105; sprintf(str, "%u.%u", value / 10, value % 10); Integer division won't be fast, but it should be faster than floating point. ...


4

You need to make sure you have checked the Use CCI Syntax option and you have #include <xc.h> in all source files. All noted in section 2.3 of the same manual.


4

Found the solution. That was that the linker options were not set to link in the peripheral library. Project properties > XC8 Linker > Options pane, Runtime selection > 'Link in Peripheral Library' option needs to be checked.


4

You seem to be using an SSD1306 oled. (worth mentioning!) To get such a display to life, you must initialize it. The sequence I use is static constexpr const uint8_t init_sequence[] = { CMD_MODE, DISPLAYOFF, CMD_MODE, SETDISPLAYCLOCKDIV, 0x80, CMD_MODE, SETMULTIPLEX, 0x3F, CMD_MODE, ...


3

I've done some looking around and here are the tips I can find Write better code. Code size and speed must be considered at each step of the way. C compiler/linker will only use the functions you actually use. So just including a .h should not increase code size (much) Standard functions are however often more generic than you require. It is possible to ...


3

void low_priority interrupt Low_Priority_Interrupt(void) { if (TMR1IE && TMR1IF) { TMR1H = 0xFE;//Pre load for 125 ms Timer1_Isr(); TMR1IF = 0; return; } } void high_priority interrupt High_Priority_Interrupt(void) { if (TX2IE && TX2IF) { SerialTx_Isr(); TX2IF = 0; return; ...


3

This is a C problem. period periods[3] = {p1, p2, p3}; is invalid in C, as p1, p2 & p3 are struct variables, and not constants known at compile-time, therefore you cannot use them as initializers. You may use macros to substitute the same constant values into p1, p2, p3 and periods[3] so that you don't have to duplicate the values: #define P1 {1, {0, ...


3

To test all below I used MPLAB 8.76, compiler XC8 ver 1.30: First a digression/advice: If you have switched to PIC16F690 recently: ~ 6 weeks ago I decided to abandon this chip, except for really small projects. It has little FLASH, little RAM and only 256 EEPROM. And you can not debug it easily on real target. I use 18FK4620 now: it has 16 times as much ...


3

ADCON1= 0b00000000; //format setup see page 182 of datasheet I think that's not right, for a start. That register controls more than just the format. Bits 0-2 control the voltage references (000 is ok for that - VDD and VSS). Bit 7 controls the format. But, bits 4-6 control the conversion clock. You set those to 000 - that equates to \$F_{OSC}/2\$. That'...


3

You are joining your HIGH and LOW byte values together wrong: unsigned int adc = ((ADRESH<<2) | ADRESL); You have a 10-bit result, 2 bits in ADRESH and 8 bits in ADRESL. Say the two values are ADRESH = 0b00000010 ADRESL = 0b10101010 You left shift the high one by 2 places, so it becomes: ADRESH = 0b00001000 ADRESL = 0b10101010 Now you OR ...


3

You should find documentation for Microchip's XC8 Peripheral Library in the 'docs' folder where you've got the XC8 compiler installed. On my PC its at C:\Program Files (x86)\Microchip\xc8\v1.21\docs The file you're looking for is MPLAB_XC8_Peripheral_Libraries.pdf I don't particularly like the documentation or their automated Doc-O-Matic system which ...


3

A few issues I see: T2CONbits.T2CKPS = 0x1; // set prescaler to 1 This line is actually setting the prescaler to 4, not 1. Based on the values you have chosen for PR2, Tosc and the TMR2 prescaler I calculate a PWM frequency of 4902 Hz. If you set the prescaler to 1 you should get a frequency of ~19608 Hz. I think this is what you intended. You should write ...


Only top voted, non community-wiki answers of a minimum length are eligible