LCD rutiner för HI-TEC C på PIC16F877?

PIC, AVR, Arduino, Raspberry Pi, Basic Stamp, PLC mm.
lasseo
Inlägg: 9
Blev medlem: 6 maj 2005, 11:24:20

LCD rutiner för HI-TEC C på PIC16F877?

Inlägg av lasseo »

Hej

Håller just på att prova HI-TEC´s C kompilator. Tvyärr får jag inte min LCD att fungera med den enkla LCD library som följde med som sample.

I ASM så har jag kört med Nigels rutiner (http://www.winpicprog.co.uk/pic_tutorial.htm), har även liknande hårdvaruuppsättning som hans tutorials.
Någon som har något bra LCD bibliotek i C?

Några andra bra länkar för HI-TECH C librarys?

// Lasseo
Användarvisningsbild
PHermansson
EF Sponsor
Inlägg: 4340
Blev medlem: 22 december 2004, 00:46:38
Ort: Särestad Grästorp
Kontakt:

Inlägg av PHermansson »

Håller på med samma sak här... har just börjat kolla koden på http://forum.microchip.com/tm.asp?m=93348&mpage=4 men ska inte säga att det funkar än.
Seven11
Inlägg: 547
Blev medlem: 13 maj 2004, 23:43:33

Inlägg av Seven11 »

jag används PICC (Hi-TecH C Compilor) när jag skrev kod för att kommunicera med en 16x2 parallell LCD. PM:a mig om du vill att jag ska skicka över koderna?
Användarvisningsbild
PHermansson
EF Sponsor
Inlägg: 4340
Blev medlem: 22 december 2004, 00:46:38
Ort: Särestad Grästorp
Kontakt:

Inlägg av PHermansson »

Hmm sitter och pillar med koden nu... håller på att slänga ut Hi-tech C.... Jag gör enklast möjliga program som tänder och sedan släcker en led. Programmet kompileras korrekt och när jag sedan kör det i processorn så blinkar led:en... Varför??
Användarvisningsbild
Icecap
Inlägg: 26226
Blev medlem: 10 januari 2005, 14:52:15
Ort: Aabenraa, Danmark

Inlägg av Icecap »

Med tanke på att du inte viser koden är det en aaaaaaning svårt att veta eller hur?
Användarvisningsbild
PHermansson
EF Sponsor
Inlägg: 4340
Blev medlem: 22 december 2004, 00:46:38
Ort: Särestad Grästorp
Kontakt:

Inlägg av PHermansson »

Så sant... tänkte mig inte för där :)

led.c:

Kod: Markera allt

#include <pic.h>
#include "delay.c"

void main(void){
	TRISB 	= 0xff;
	TRISC	= 0x00;
	TRISE   = 0x00;
	PORTB	= 0x00;
	PORTC	= 0x00;
	PORTE   = 0x00;	

		//led on
		RE0=0;
	   //Wait...
		DelayMs(200);
		DelayMs(200);
		DelayMs(200);
		DelayMs(200);
		//led off
		RE0=1;   
		//Wait...
		DelayMs(200);
}
delay.c:

Kod: Markera allt

/*

high level delay routines - see delay.h for more info.

Designed by Shane Tolmie of KeyGhost corporation.  Freely distributable.
Questions and comments to shane@keyghost.com
PICuWEB - Program PIC micros with C. Site has FAQ and sample source code. http://www.workingtex.com/htpic

For Microchip 12C67x, 16C7x, 16F87x and Hi-Tech C

*/

#ifndef __DELAY_C
#define __DELAY_C

#include <pic.h>
#include	"always.h"

unsigned char delayus_variable;

#include	"delay.h"

void DelayBigUs(unsigned int cnt)
{
	unsigned char	i;

	i = (unsigned char)(cnt>>8);
	while(i>=1)
	{
		i--;
		DelayUs(253);
		CLRWDT();
	}
	DelayUs((unsigned char)(cnt & 0xFF));
}

void DelayMs(unsigned char cnt)
{
	unsigned char	i;
	do {
		i = 4;
		do {
			DelayUs(250);
			CLRWDT();
		} while(--i);
	} while(--cnt);
}

//this copy is for the interrupt function
void DelayMs_interrupt(unsigned char cnt)
{
	unsigned char	i;
	do {
		i = 4;
		do {
			DelayUs(250);
		} while(--i);
	} while(--cnt);
}

void DelayBigMs(unsigned int cnt)
{
	unsigned char	i;
	do {
		i = 4;
		do {
			DelayUs(250);
			CLRWDT();
		} while(--i);
	} while(--cnt);
}

void DelayS(unsigned char cnt)
{
	unsigned char i;
	do {
		i = 4;
		do {
			DelayMs(250);
			CLRWDT();
		} while(--i);
	} while(--cnt);
}

#endif
delay.h:

Kod: Markera allt

#define PIC_CLK 20000000 //16Mhz

/*

lowlevel delay routines

Designed by Shane Tolmie of KeyGhost corporation.  Freely distributable.
Questions and comments to shane@workingtex.com
PICuWEB - Program PIC micros with C. Site has FAQ and sample source code.
http://www.workingtex.com/htpic/

For Microchip 12C67x, 16C7x, 16F87x and Hi-Tech C

Example C:

#define PIC_CLK 4000000

#include "delay.h"

unsigned int timeout_int, timeout_char;

DelayUs(40);  //do NOT do DelayUs(N) of N<5 @ 4Mhz or else it executes DelayUs(255) !!!!
DelayUs(255); //max

dly250n;      //delay 250ns
dly1u;        //delay 1us

timeout_char=timeout_char_us(1147);
while(timeout_char-- && (RA1==0));  //wait up to 1147us for port RA1 to go high
				    //  - this is the max timeout

timeout_int=timeout_int_us(491512);
while(timeout_int-- && (RA1==0));   //wait up to 491512us for port RA1 to go high
				    //  - this is the max timeout

*/

#ifndef __DELAY_H
#define __DELAY_H

extern unsigned char delayus_variable;

#if (PIC_CLK == 4000000)
	#define dly125n please remove; for 32Mhz+ only
	#define dly250n please remove; for 16Mhz+ only
	#define dly500n please remove; for 8Mhz+ only
	#define dly1u asm("nop")
	#define dly2u dly1u;dly1u
#elif (PIC_CLK == 8000000)
	#define dly125n please remove; for 32Mhz+ only
	#define dly250n please remove; for 16Mhz+ only
	#define dly500n asm("nop")
	#define dly1u dly500n;dly500n
	#define dly2u dly1u;dly1u
#elif ( (PIC_CLK == 16000000) || (PIC_CLK == 16257000) )
	#define dly125n please remove; for 32Mhz+ only
	#define dly250n asm("nop")
	#define dly500n dly250n;dly250n
	#define dly1u dly500n;dly500n
	#define dly2u dly1u;dly1u
#elif (PIC_CLK == 20000000)
	#define dly200n asm("nop")
	#define dly400n dly250n;dly250n
	#define dly2u dly400n;dly400n;dly400n;dly400n;dly400n
#elif (PIC_CLK == 32000000)
	#define dly125n asm("nop")
	#define dly250n dly125n;dly125n
	#define dly500n dly250n;dly250n
	#define dly1u dly500n;dly500n
	#define dly2u dly1u;dly1u
#else
	#error delay.h - please define pic_clk correctly
#endif

//*****
//delay routine

#if PIC_CLK == 4000000
	#define DelayDivisor 4
	#define WaitFor1Us asm("nop")
	#define Jumpback asm("goto $ - 2")
#elif PIC_CLK == 8000000
	#define DelayDivisor 2
	#define WaitFor1Us asm("nop")
	#define Jumpback asm("goto $ - 2")
#elif ( (PIC_CLK == 16000000) || (PIC_CLK==16257000) )
	#define DelayDivisor 1
	#define WaitFor1Us asm("nop")
	#define Jumpback asm("goto $ - 2")
#elif PIC_CLK == 20000000
	#define DelayDivisor 1
	#define WaitFor1Us asm("nop"); asm("nop")
	#define Jumpback asm("goto $ - 3")
#elif PIC_CLK == 32000000
	#define DelayDivisor 1
	#define WaitFor1Us asm("nop"); asm("nop"); asm("nop"); asm("nop"); asm("nop")
	#define Jumpback asm("goto $ - 6")
#else
	#error delay.h - please define pic_clk correctly
#endif

#define DelayUs(x) { \
			delayus_variable=(unsigned char)(x/DelayDivisor); \
			WaitFor1Us; } \
			asm("decfsz _delayus_variable,f"); \
			Jumpback;

/*

timeouts:

C code for testing with ints:

			unsigned int timeout;
			timeout=4000;
			PORT_DIRECTION=OUTPUT;
			while(1)
			{
				PORT=1;
				timeout=8000;
				while(timeout-- >= 1);	//60ms @ 8Mhz, opt on, 72ms @ 8Mhz, opt off
				PORT=0;
			}

Time taken:	optimisations on:		16cyc/number loop, 8us @ 8Mhz
			optimisations off:		18cyc/number loop, 9us @ 8Mhz
			with extra check ie:	&& (RB7==1), +3cyc/number loop, +1.5us @ 8Mhz

C code for testing with chars:

			similar to above

Time taken:	optimisations on:		9cyc/number loop, 4.5us @ 8Mhz
			with extra check ie:	&& (RB7==1), +3cyc/number loop, +1.5us @ 8Mhz

Formula:	rough timeout value = (<us desired>/<cycles per loop>) * (PIC_CLK/4.0)

To use:		//for max  timeout of 1147us @ 8Mhz
			#define LOOP_CYCLES_CHAR	9					//how many cycles per loop, optimizations on
			#define timeout_char_us(x)	(unsigned char)((x/LOOP_CYCLES_CHAR)*(PIC_CLK/4.0))
			unsigned char timeout;
			timeout=timeout_char_us(1147);						//max timeout allowed @ 8Mhz, 573us @ 16Mhz
			while((timeout-- >= 1) && (<extra condition>));	//wait

To use:		//for max 491512us, half sec timeout @ 8Mhz
			#define LOOP_CYCLES_INT		16					//how many cycles per loop, optimizations on
			#define timeout_int_us(x)	(unsigned int)((x+/LOOP_CYCLES_INT)*(PIC_CLK/4.0))
			unsigned int timeout;
			timeout=timeout_int_us(491512);						//max timeout allowed @ 8Mhz
			while((timeout-- >= 1) && (<extra condition>));	//wait
*/
#define LOOP_CYCLES_CHAR	9							//how many cycles per loop, optimizations on
#define timeout_char_us(x)	(long)(((x)/LOOP_CYCLES_CHAR)*(PIC_CLK/1000000/4))

#define LOOP_CYCLES_INT		16							//how many cycles per loop, optimizations on
#define timeout_int_us(x)	(long)(((x)/LOOP_CYCLES_INT)*(PIC_CLK/1000000/4))

//if lo byte is zero, faster initialization by 1 instrucion
#define timeout_int_lobyte_zero_us(x)	(long)(((x)/LOOP_CYCLES_INT)*(PIC_CLK/4.0)&0xFF00)

//function prototypes
void DelayBigUs(unsigned int cnt);
void DelayMs(unsigned char cnt);
void DelayMs_interrupt(unsigned char cnt);
void DelayBigMs(unsigned int cnt);
void DelayS(unsigned char cnt);

#endif


Användarvisningsbild
sodjan
EF Sponsor
Inlägg: 43205
Blev medlem: 10 maj 2005, 16:29:20
Ort: Söderköping
Kontakt:

Inlägg av sodjan »

Vad gör PICC när main() har "tagit slut" ?
Min gissning är att PC snurrar runt tillbaka till h'0000'
efter ett litet tag och allt startar om igen.
Då måste antagligen "låsa upp" processorn på slutet med
en oändlig loop. Jag kan inte C men det finns säker sätt...
Användarvisningsbild
PHermansson
EF Sponsor
Inlägg: 4340
Blev medlem: 22 december 2004, 00:46:38
Ort: Särestad Grästorp
Kontakt:

Inlägg av PHermansson »

Skulle man kunna tro... så jag lägger till:

Kod: Markera allt

while(1); {
}
sist i main() men det gör ingen skillnad.
Användarvisningsbild
Icecap
Inlägg: 26226
Blev medlem: 10 januari 2005, 14:52:15
Ort: Aabenraa, Danmark

Inlägg av Icecap »

Det räcker helt fint med
while(1);

Du kan även skriva:
while(1)
{
}

En del kompilers föredrar den versionen när det är tomt statement.
Användarvisningsbild
sodjan
EF Sponsor
Inlägg: 43205
Blev medlem: 10 maj 2005, 16:29:20
Ort: Söderköping
Kontakt:

Inlägg av sodjan »

WDT ?
Hur "fort" blinkar dioden ?
Senast redigerad av sodjan 19 maj 2005, 13:21:18, redigerad totalt 1 gång.
Användarvisningsbild
PHermansson
EF Sponsor
Inlägg: 4340
Blev medlem: 22 december 2004, 00:46:38
Ort: Särestad Grästorp
Kontakt:

Inlägg av PHermansson »

blink, blink.... while(1) hjälper inte...
Användarvisningsbild
PHermansson
EF Sponsor
Inlägg: 4340
Blev medlem: 22 december 2004, 00:46:38
Ort: Särestad Grästorp
Kontakt:

Inlägg av PHermansson »

:) And finally... Sodjan - 12 points!

Det var en luring - hade stängt av WDT i MPLAB så jag trodde inte det var det. Problemet var bara att min programmeringsmjukvara satte på WDT oavsett vad MPLAB var inställt på.
Nu funkar det, tack!

Testade med while och utan while nu oxå... verkar göra skillnad, utan while blinkar det men inte med.
Användarvisningsbild
sodjan
EF Sponsor
Inlägg: 43205
Blev medlem: 10 maj 2005, 16:29:20
Ort: Söderköping
Kontakt:

Inlägg av sodjan »

Elementary, my dear Watson... :-)

Kan man inte ange CONFIG'en direct i PICC ?
D.v.s så att de kommer med i HEX filen. Sedan skall
naturligtsvis inte programmeringsmjukvaran ändra något !

Det finns igentligen ingen som helst anledning att ändra "fuses"
efter att HEX filen är genererad. HEX filen skall vara komplett och
programmeringsmjukvaran skall bara blåsa in den i PIC'en utan
att ändra något.
Seven11
Inlägg: 547
Blev medlem: 13 maj 2004, 23:43:33

Inlägg av Seven11 »

jo det kan du:

Kod: Markera allt

__CONFIG( CONFIGDATA );
Där CONFIGDATA är configurations bitarna (ur pic1684.inc):
/*osc configurations*/
#define RC 0x3FFF // resistor/capacitor
#define HS 0x3FFE // high speed crystal/resonator
#define XT 0x3FFD // crystal/resonator
#define LP 0x3FFC // low power crystal/resonator

/*watchdog*/
#define WDTEN 0x3FFF // enable watchdog timer
#define WDTDIS 0x3FFB // disable watchdog timer

/*power up timer*/
#if defined (_16C84)
#define PWRTEN 0x3FFF /* enable power up timer*/
#define PWRTDIS 0x3FF7 /* disable power up timer */
#else
#define PWRTDIS 0x3FFF /* disable power up timer */
#define PWRTEN 0x3FF7 /* enable power up timer */
#endif

#if defined (_16CR83) || defined(_16CR84)
#define DP 0x3F7F // data code is protected
#define PROTECT 0x008F // program code is protected
// alternative definition
#define DATPROT 0x3F7F // use DP
#define DATUNPROT 0x3FFF // use UNPROTECT
#elif defined (_16C84)
#define PROTECT 0x3FEF // program code is protected
#elif defined (_16F83) || defined(_16F84) || defined(_16F84A)
#define PROTECT 0x000F // program code is protected
#endif

#define UNPROTECT 0x3FFF // do not protect the code
Men inkludera "pic.h" i din kod så kommer PICC automatiskt inkludera rätt modell fil (typ pic1684.inc om du i MPLAB har ställt in att du ska programmera en PIC16F84A..

Så allt du behöver göra är: __CONFIG(XT & WDTDIS & PWRTDIS & UNPROTECT);
Användarvisningsbild
sodjan
EF Sponsor
Inlägg: 43205
Blev medlem: 10 maj 2005, 16:29:20
Ort: Söderköping
Kontakt:

Inlägg av sodjan »

Precis !
Och det är där de skall vara (i källkoden).
Varken i MPLAB's konfiguration eller i någon programmeringsprogramvara...

Varför ?
Jo därför att när man ett år senare plockar fram sitt gamla projekt, så behöver man inte sitta och slita sitt hår över hur inställningarna var. Bara ladda och bygg om projektet så blir allt rätt direkt.

Slutligen, ditt exempel var från en F84'a. Vi får väll hoppas att ingen fortfarande använder den gamla processorn...
Skriv svar