@Guiseppe Straight question. So, I do not waste my time.
Are you aiming to enable the Slave for this micrcontrolller? Why am I asking? I have in my IDE a AN734 library for the K42s with call backs to support incoming and outgoing slave communications. But, if you are wanting to complete without this library I would put this on bottom of the list of things to do.
Let me know.
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
@Guiseppe. I have opened up another ticket with Microchip. I cannot get the Slave to operate, at all, even when using MPLAB-X 4.01 I used code provided by Microchip and I get no response. If you get things working that would be great.
My ticket has a couple asks.
1. Example/working code for slave responding to MCP2221 MCP/Bus discovery tool
2. Example/working code for write operation using MCP2221 MCP/Bus tool
3. Example/working code for read operation using MCP2221 MCP/Bus tool
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
So, far. I have updated the chip.dat file (this will need to be done to all K42 chips), updated HWi2c.h library to add the slave support, revised the exiting two slave libraries to support KMode.
I can get the intrerface to respond once, only once. Then, I have to resprogram. Somehting is not right.
Also the I2C sending I believe works fine. However my LCD is not compatible with the instructions #define LCD_IO 10 or #define LCD_IO 12.
Accordingly, the words shown on the LCD are not the ones expected as shown on the terminal and some special character also is shown.
I tested also the code 310_IC2_LCD_Adapter_using_HardwareI2C_18f25k42 available for 18F25K42 in the ChipRange Demonstrations installation directory.
The behaviour is the same as for William code. The LCD changes according to the code sequence although the characters are not correct. Again I believe this is due to the fact that my LCD is not compatible with the code.
As a conclusion, I'm quite sure that the codes I tested works on 18F45k42 although I have not a full demonstration.
I thank you for the program showing the I2C registers you sent.
I think it will be very useful.
In the meantime after a lot of attempts I got a code able to manage the PIC as a slave. Obviously it is not complete and it is not really clear to me why it works and how stable it is.
It is only a first step. As the examples you sent me show, I think I must manage the interrupts in a more effective way by using GCBASIC oninterrupt commands.
I attach the code (there are 3 versions of the subroutine sertxd I use for printing on terminal. The Master send two byte each time and I want to read six bytes) :
#chip18F45k42,64#optionexplicit#configMCLRE=ON#startupInitPPS,85'//Call InitPPS'_____________'I2CSETODCONC.ODCC4onSETODCONC.ODCC3onSETRC3I2C.TH0OFF'Portspecificcontrolsmayberequired-seethedatasheetSETRC4I2C.TH0OFF'Portspecificcontrolsmayberequired-seethedatasheet'SetpinI2CdirectionsDirPORTC.4OutDirPORTC.3Out'DefineI2Csettings#defineHI2C_BAUD_RATE100#defineHI2C_DATAPORTC.4#defineHI2C_CLOCKPORTC.3'NowsetuptheI2CslaveHI2CModeSlaveHI2CSetAddress0xA0'=esadecimale'inbinario=b'10100000'SETI2C1ADR0=0xA0SETI2C1CON0.MODE0=0'setSlavemode,fourbitaddressSETI2C1CON0.MODE1=0SETI2C1CON0.MODE2=0'______________'USART#defineUSART_BAUD_RATE9600#defineUSART_DELAY5ms#defineUSART_BLOCKING'SetpinUSARTdirectionsDirportC.7INDirportC.6OUT'---Portsettings____________'LEDS#defineled1portA.6'DirportA.6OUT'__Variables_________#defineDim_Array10dimVar_Array(Dim_Array)Dimn_elmasByteDimindasByteDimAddressasByte'=============Code======================main:wait500msled1=1Repeat5LED1=!LED1wait300msLED1=!LED1wait300msendRepeatAddress=0sertxd(1,"=== Test"," I2C receive",1)forind=0toDim_ArrayVar_Array(ind)=0NextMyHI2CReceive(n_elm)sertxd(1,"data number=",n_elm,0)sertxd(1,"received: address=",Address,0)forind=1ton_elmifind=1Thensertxd(1," Var_Array=",Var_Array(ind),0)Elsesertxd(9," ",Var_Array(ind),0)EndIfNextsertxd(1,"I2C1CNT=",I2C1CNT,1)gotomainSubMyHI2CReceive(n_elm)DimCOUNT_readasbyten_elm=1PCIF=0I2C1CNT=100count_read=I2C1CNTdountilcount_read<95SETI2C1PIR=0SETI2C1PIE.ACKTIEON'EnableacknowledgeclockstretchingSETI2C1PIE.PCIEON'EnableSTOPconditioninterruptsertxd(1,"waiting ","inside loop",0)sertxd(9,"I2C1CNT=",I2C1CNT,0)WaituntilI2C1IF=1''WaitforreceiveaddressADDRESS=I2C1ADB0SETI2C1CON1.ACKDTOFF‘AckowledgeSETI2C1CON0.CSTROFF'ReleaseSCLWaituntilI2C1RXIF=1Var_Array(n_elm)=I2C1RXBn_elm=n_elm+1wait20usSETI2C1CON0.CSTROFF'ReleaseSCLWaituntilI2C1RXIF=1Var_Array(n_elm)=I2C1RXBn_elm=n_elm+1wait20usSETI2C1CON0.CSTROFF'ReleaseSCLcount_read=I2C1CNTwait50usLoopn_elm=n_elm-1EndSub‘_________________________________________SUBSertxd(inCRLF1asbyte,instringaasstring,ininputSasString,inCRLF2asbyte)ifCRLF1<2ThenHSerPrintCRLFCRLF1ElseHSerSendCRLF1EndifHSerPrintstringaHSerPrintinputSifCRLF2<2ThenHSerPrintCRLFCRLF2ElseHSerSendCRLF2EndifENDSUB‘________________________________SUBSertxd(inCRLF1asbyte,instringaasString,ininputBasByte,inCRLF2asByte)ifCRLF1<2ThenHSerPrintCRLFCRLF1ElseHSerSendCRLF1EndifHSerPrintstringaHSerPrintinputBifCRLF2<2ThenHSerPrintCRLFCRLF2ElseHSerSendCRLF2EndifENDSUB‘______________________________________SUBSertxd(inCRLF1asbyte,instringaasstring,ininputWasWord,inCRLF2asbyte)ifCRLF1<2ThenHSerPrintCRLFCRLF1ElseHSerSendCRLF1EndifHSerPrintstringaHSerPrintinputWifCRLF2<2ThenHSerPrintCRLFCRLF2ElseHSerSendCRLF2EndifENDSUB‘__________________________________________________SubInitPPS'//sets up pins for USARTUNLOCKPPS'Module:UART1U1RXPPS=0x0017'RC7>RX1RC6PPS=0x0013'TX1>RC6'Module:I2C1'inputI2C1SCLPPS=0x0013I2C1SDAPPS=0x0014'OutputRC3PPS=0x0021RC4PPS=0x0022LOCKPPSEndSub
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
@Anobium
before my last post I did'nt seen your last posts (they are on page 2 and I have not noticed it).
As a matter of fact the code I sent, apart from the heavness due to the printing routines, is short and works although is not really stable. I receive two bytes at a time.
I found many difficulties because I was not able using many interrupts like ADRIF, WRIF, PCIE, although I enabled them by properly setting the PIE register bits.
And this was in contrast with the step by step procedure depicted in the PIC datasheet.
At the end I decided to use the ACKTIE enable (the one I excluded at the beginning) and to use the general interrupt I2C1IF for address receiving step managing.
I managed the received bytes by using the I2C1RXIF interrupt, described in the step by step procedure.
However, I needed a delay before releasing the SCL. (I used 20 us). I do not understand why.
All this is a result of intuition, not knowledge, because the PIC has a strange, unpredictable behaviour.
And also for me sometimes it stops and a reprogramming is needed.
Concerning your Stright question, obviously my aim is to have a working I2C slave (for receiving data only, at the moment). Although I also would like to understand how things works. A library provides a large amount of information often not exactly understandable when having the little experience I have.
Obviously in this way I lose a lot of time.
Thenk you again for your attention.
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
You are making things difficult for youtself if your goal is to get reliable I2cSlave functionality in a project within a reasonable time . For this project you have selected the 18F45K42 which is one of the most complicated (and least supported) PIC chips available.
Unless you enjoy the frustration that goes with working with a chip that is possibly buggy and not fully supported, and you don't mind the time an frustration involved, I would suggest you use a different chip, until the issues are worked out of the K42 series of chips. It could be weeks or even months before I2C is stable on this chip.
When you you want to have a reliable working project?
Why did you select 18F45K42? Speed? Memory? Specific Peripherals?
There are other 18F PIC Chips that can do I2C slave right now. These do not have the complexity of PPS, ...Do not have the "new and unproven" I2C modues and can still run at 64MHz (if you are a speed demon). 18F45K80 ... 18F45K22 .. etc. There are many 16F Chips that can do this as well, some with PPS and some not.
LCD:
Your LCD module is an odball and uses special commands that are explained in the datasheet you posted. It will not work with any GCB LCD Libraries. Suggest you lay it aside and get a more common type that is fully supported. These cost about $6 - $8 on Ebay last time i checked.
Otherwise you will need to write your own code to use it effectively. And then you will likely be the only person that ever uses it.
I already used 18F45k22 as a Picaxe chip, with an external 16MHz cristal and an internal 4x multipler clock frequency. I programmed it using Picaxe Editor without problems. I still have one such chip available.
My application now involves the CNC axes control trough a "real time" PIC under the supervision of a Rpi zero. My application, using the Picaxe 18F45k22, runs fine at the moment.
However, I would run the PIC application code as fast as possible and, unfortunately, Picaxe uses an interpreter that slow down the code execution.
Accordingly, I decided to program by myself the PIC and I found GCBASIC. And PicKit3 and IDE and IPE...
However, I decided to not use the available 18F45k22 exploiting GCBASIC in order to not destroy the Picaxe firmware bootstrap code in the chip.
Obviously, I might have bought other PIC18F45k22.
I chosen the PIC 18F45k42 because it allows internall 64MHz clock and has huge memory and, mainly, because is an upgrade (I supposed that) with respect to 18F45k22.
Without being an expert, I did not imagine the difficulties of this my first PIC programming experience.
This is the story.
However, following your considerations, now I will buy a 18F45k22 and I will program it with a less effort, I hope.
I had not become frightened for the effort of programming the 18F45k42. It was of great interest and I still will try to solve the problems with 42 PIC as a lost time.
I sincerely thanks you and Anobium for all the support you gave me on that PIC and for your pacience.
Concerning the LCD, yes I agree with you on the benefits of buying a more update LCD.
I surely will do it.
I used the old LCD because it was the one already available at the moment and it would have given me pleasure to quicly test the demonstration codes you sent and suggested.
Thank you all
Sincerely yours
Giuseppe
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
within this post I do not want to re-open the last question discussed recently.
My last post still holds.
I just want report my last results on making a Slave reception with PIC18F45k42.
There are not controls on overflow or any other kind of errors handling in the subroutine.
However is what could be enough for me.
In the following I attach the PIC settings and the subroutine I used for PIC18F45k42 slave receiving.
Now everyting works and the behaviour seem to be stable.
I texted the code by sending two bytes as well as five bytes, at the moment.
I have a first PIC sending a sequence of bytes on the I2C channel when I press a button.
PIC18F45k42 receive the bytes on the same channel and print them on the Cool terminal.
Note:
I already attempted to run a subroutine like that many times without success.
I discovered that if I use PCIF instead than I2C1PIR.PCIF I cannot detect the stop condition, i.e., PCIF stay 0 while I2C1PIR.PCIF becomes equal to 1 at the stop condition.
I don't know way.
I looked the PIC database and I noted that, while PIC name appears in the line PCIF,I2C2PIR,2 for I2C2, it appears in the line I2C1PIR_PCIF,I2C1PIR,2 for I2C1 channel.
Different ways are used for I2C2 and I2C1. Obviously, I do not know why.
Just a note.
I hope this can help you.
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
This is because the Microchip bit naming convention is inconsistent in the Microchip files we use to make the GCB chip datafile from.
Short names like "PCIF" may not work as expected so when worlking with new chips is is generally a good practice to use "register.bit" instead of the short name.
You can always look in the Chip Datafile to see what the bit name should be used.
For example:
Open the file 18F45K42.dat in GreatDowBasic\chipdata. Then search for PCIF. You will find 2 lines. One shows its usage with I2C2 and the other with I2C1. "PCIF" is used for I2C2 while I2C1PIR_PCIF is used for I2C1 in the Great Cow BASIC dat file - this bit should be access via I2C1PIR.PCIF where you transpose the _ with a period.
Further down a few lines you will see "PC1IF,I2C1PIR,2""
This is can look inconsistent and confusing, and can lead to problems if you are not very careful
So for I2C1 you can use any of these :
I2C1PIR.PCIF
I2C1PIR.2
PC1IF
This may apply to other registers as well. Always look in the chip datafile to get the correct regiater name if you are not using (register,bit)
You can test this by creating a simple program, compiling, then looking at the ASM file
GCB Program
Set PCIF OFF
Set PC1IF OFF
Now Look at the ASM file. You will see ...
~~~
;set PCIF OFF
banksel I2C2PIR
bcf I2C2PIR,PCIF,BANKED
;set PC1IF OFF
bcf I2C1PIR,PC1IF,BANKED
~~~
Edited by Anobium.
Last edit: Anobium 2017-11-30
If you would like to refer to this comment somewhere else in this project, copy and paste the following link:
@Guiseppe Straight question. So, I do not waste my time.
Are you aiming to enable the Slave for this micrcontrolller? Why am I asking? I have in my IDE a AN734 library for the K42s with call backs to support incoming and outgoing slave communications. But, if you are wanting to complete without this library I would put this on bottom of the list of things to do.
Let me know.
@Guiseppe. I have opened up another ticket with Microchip. I cannot get the Slave to operate, at all, even when using MPLAB-X 4.01 I used code provided by Microchip and I get no response. If you get things working that would be great.
My ticket has a couple asks.
1. Example/working code for slave responding to MCP2221 MCP/Bus discovery tool
2. Example/working code for write operation using MCP2221 MCP/Bus tool
3. Example/working code for read operation using MCP2221 MCP/Bus tool
Bit of an updated... Using Great Cow BASIC....
A response..... for the initialisation of
I got this from the MCP2221. Which is a result!
So, far. I have updated the chip.dat file (this will need to be done to all K42 chips), updated HWi2c.h library to add the slave support, revised the exiting two slave libraries to support KMode.
I can get the intrerface to respond once, only once. Then, I have to resprogram. Somehting is not right.
Last edit: Anobium 2017-11-26
@Anobium and William ,
I found my old LCD (LCD03 - I2C/Serial LCD, see at http://www.robot-electronics.co.uk/htm/Lcd03tech.htm) and tested the I2C + Serial test program William sent in a previous post.
The serial sending works fine.
Also the I2C sending I believe works fine. However my LCD is not compatible with the instructions #define LCD_IO 10 or #define LCD_IO 12.
Accordingly, the words shown on the LCD are not the ones expected as shown on the terminal and some special character also is shown.
I tested also the code 310_IC2_LCD_Adapter_using_HardwareI2C_18f25k42 available for 18F25K42 in the ChipRange Demonstrations installation directory.
The behaviour is the same as for William code. The LCD changes according to the code sequence although the characters are not correct. Again I believe this is due to the fact that my LCD is not compatible with the code.
As a conclusion, I'm quite sure that the codes I tested works on 18F45k42 although I have not a full demonstration.
I thank you for the program showing the I2C registers you sent.
I think it will be very useful.
In the meantime after a lot of attempts I got a code able to manage the PIC as a slave. Obviously it is not complete and it is not really clear to me why it works and how stable it is.
It is only a first step. As the examples you sent me show, I think I must manage the interrupts in a more effective way by using GCBASIC oninterrupt commands.
I attach the code (there are 3 versions of the subroutine sertxd I use for printing on terminal. The Master send two byte each time and I want to read six bytes) :
@Anobium
before my last post I did'nt seen your last posts (they are on page 2 and I have not noticed it).
As a matter of fact the code I sent, apart from the heavness due to the printing routines, is short and works although is not really stable. I receive two bytes at a time.
I found many difficulties because I was not able using many interrupts like ADRIF, WRIF, PCIE, although I enabled them by properly setting the PIE register bits.
And this was in contrast with the step by step procedure depicted in the PIC datasheet.
At the end I decided to use the ACKTIE enable (the one I excluded at the beginning) and to use the general interrupt I2C1IF for address receiving step managing.
I managed the received bytes by using the I2C1RXIF interrupt, described in the step by step procedure.
However, I needed a delay before releasing the SCL. (I used 20 us). I do not understand why.
All this is a result of intuition, not knowledge, because the PIC has a strange, unpredictable behaviour.
And also for me sometimes it stops and a reprogramming is needed.
Concerning your Stright question, obviously my aim is to have a working I2C slave (for receiving data only, at the moment). Although I also would like to understand how things works. A library provides a large amount of information often not exactly understandable when having the little experience I have.
Obviously in this way I lose a lot of time.
Thenk you again for your attention.
@Guiseppe
You are making things difficult for youtself if your goal is to get reliable I2cSlave functionality in a project within a reasonable time . For this project you have selected the 18F45K42 which is one of the most complicated (and least supported) PIC chips available.
Unless you enjoy the frustration that goes with working with a chip that is possibly buggy and not fully supported, and you don't mind the time an frustration involved, I would suggest you use a different chip, until the issues are worked out of the K42 series of chips. It could be weeks or even months before I2C is stable on this chip.
When you you want to have a reliable working project?
Why did you select 18F45K42? Speed? Memory? Specific Peripherals?
There are other 18F PIC Chips that can do I2C slave right now. These do not have the complexity of PPS, ...Do not have the "new and unproven" I2C modues and can still run at 64MHz (if you are a speed demon). 18F45K80 ... 18F45K22 .. etc. There are many 16F Chips that can do this as well, some with PPS and some not.
LCD:
Your LCD module is an odball and uses special commands that are explained in the datasheet you posted. It will not work with any GCB LCD Libraries. Suggest you lay it aside and get a more common type that is fully supported. These cost about $6 - $8 on Ebay last time i checked.
Otherwise you will need to write your own code to use it effectively. And then you will likely be the only person that ever uses it.
https://www.ebay.com/itm/Yellow-Green-Serial-IIC-I2C-TWI-2004-LCD-20X4-Character-LCD-Module-For-Arduino/201013825839?hash=item2ecd5b912f:g:BHwAAOSwvg9XcPwD
https://www.ebay.com/itm/Blue-Serial-IIC-I2C-TWI-2004-204-20X4-Character-LCD-Module-Display-For-Arduino/381375068233?epid=894371540&hash=item58cbb9b849:g:oL8AAOSwFAZTviYj
@William and Anobium
I agree with your considerations.
I already used 18F45k22 as a Picaxe chip, with an external 16MHz cristal and an internal 4x multipler clock frequency. I programmed it using Picaxe Editor without problems. I still have one such chip available.
My application now involves the CNC axes control trough a "real time" PIC under the supervision of a Rpi zero. My application, using the Picaxe 18F45k22, runs fine at the moment.
However, I would run the PIC application code as fast as possible and, unfortunately, Picaxe uses an interpreter that slow down the code execution.
Accordingly, I decided to program by myself the PIC and I found GCBASIC. And PicKit3 and IDE and IPE...
However, I decided to not use the available 18F45k22 exploiting GCBASIC in order to not destroy the Picaxe firmware bootstrap code in the chip.
Obviously, I might have bought other PIC18F45k22.
I chosen the PIC 18F45k42 because it allows internall 64MHz clock and has huge memory and, mainly, because is an upgrade (I supposed that) with respect to 18F45k22.
Without being an expert, I did not imagine the difficulties of this my first PIC programming experience.
This is the story.
However, following your considerations, now I will buy a 18F45k22 and I will program it with a less effort, I hope.
I had not become frightened for the effort of programming the 18F45k42. It was of great interest and I still will try to solve the problems with 42 PIC as a lost time.
I sincerely thanks you and Anobium for all the support you gave me on that PIC and for your pacience.
Concerning the LCD, yes I agree with you on the benefits of buying a more update LCD.
I surely will do it.
I used the old LCD because it was the one already available at the moment and it would have given me pleasure to quicly test the demonstration codes you sent and suggested.
Thank you all
Sincerely yours
Giuseppe
Hi Anobium and William
within this post I do not want to re-open the last question discussed recently.
My last post still holds.
I just want report my last results on making a Slave reception with PIC18F45k42.
There are not controls on overflow or any other kind of errors handling in the subroutine.
However is what could be enough for me.
In the following I attach the PIC settings and the subroutine I used for PIC18F45k42 slave receiving.
Now everyting works and the behaviour seem to be stable.
I texted the code by sending two bytes as well as five bytes, at the moment.
I have a first PIC sending a sequence of bytes on the I2C channel when I press a button.
PIC18F45k42 receive the bytes on the same channel and print them on the Cool terminal.
Here is the PIC settings I used
Here is the subroutine:
Note:
I already attempted to run a subroutine like that many times without success.
I discovered that if I use PCIF instead than I2C1PIR.PCIF I cannot detect the stop condition, i.e., PCIF stay 0 while I2C1PIR.PCIF becomes equal to 1 at the stop condition.
I don't know way.
I looked the PIC database and I noted that, while PIC name appears in the line PCIF,I2C2PIR,2 for I2C2, it appears in the line I2C1PIR_PCIF,I2C1PIR,2 for I2C1 channel.
Different ways are used for I2C2 and I2C1. Obviously, I do not know why.
Just a note.
I hope this can help you.
This is because the Microchip bit naming convention is inconsistent in the Microchip files we use to make the GCB chip datafile from.
Short names like "PCIF" may not work as expected so when worlking with new chips is is generally a good practice to use "register.bit" instead of the short name.
You can always look in the Chip Datafile to see what the bit name should be used.
For example:
Open the file 18F45K42.dat in GreatDowBasic\chipdata. Then search for PCIF. You will find 2 lines. One shows its usage with I2C2 and the other with I2C1. "PCIF" is used for I2C2 while I2C1PIR_PCIF is used for I2C1 in the Great Cow BASIC dat file - this bit should be access via I2C1PIR.PCIF where you transpose the _ with a period.
Further down a few lines you will see "PC1IF,I2C1PIR,2""
This is can look inconsistent and confusing, and can lead to problems if you are not very careful
So for I2C1 you can use any of these :
I2C1PIR.PCIF
I2C1PIR.2
PC1IF
This may apply to other registers as well. Always look in the chip datafile to get the correct regiater name if you are not using (register,bit)
You can test this by creating a simple program, compiling, then looking at the ASM file
GCB Program
Now Look at the ASM file. You will see ...
~~~
;set PCIF OFF
banksel I2C2PIR
bcf I2C2PIR,PCIF,BANKED
;set PC1IF OFF
bcf I2C1PIR,PC1IF,BANKED
~~~
Edited by Anobium.
Last edit: Anobium 2017-11-30