Continue to Site

Welcome to our site!

Electro Tech is an online community (with over 170,000 members) who enjoy talking about and building electronic circuits, projects and gadgets. To participate you need to register. Registration is free. Click here to register now.

  • Welcome to our site! Electro Tech is an online community (with over 170,000 members) who enjoy talking about and building electronic circuits, projects and gadgets. To participate you need to register. Registration is free. Click here to register now.

Question about reading bits from ports.

Status
Not open for further replies.

Blueteeth

Well-Known Member
Hi,
I posted a question a while back about interfacing a PIC to a 16-bit ADC, after building a programmer and relearning assembly code I've come a long way, but there is one more issue :cry:

First of all, general question(s):
Is a 'bit-test' (btfss) the ONLY way to get a bit from a single port pin?

If PORTB has 7 outputs and 1 input, is it possible to simply move PORTB to W, and then move this stored number to PORTA? Leaving the input from PORTB as an output on PORTA(as well as the 7 outputs from PORTB)?

Secondly, my problem.....
What I am doing is clocking an ADC, and reading the data from it. However, I'm not planning to store any data, I have a subroutine which roughly looks like this...

Code:
SAMPLE

BSF       PORTB,1      ;make clock high
MOVWF     PORTB,2      ;read the data input and store it in W (WRONG)
MOVLW     PORTA,0      ;send the data bit to output               (WRONG)
NOP                         ;wasted cycle, to equal m/s ratio of clock.
BCF       PORTB,1      ;make clock low
DECFSZ    Count,1    ;count = 16 for  the sub' to run 16 times, dec count
GOTO      SAMPLE       ; if count is non-zero take another sample
RETURN                   ;if count is zero, go back to main program

As you can see, lines 2 and 3 are incorrect, but it shows what I want to do.

Timing is critical, the maximum number of cycles for a sample is 6 or 8.
So thats 3 (or 4) instruction cycles for the clock high, and the same for the clock low. Say the sample would take 8 cycles, just for convienience..
Therefore, 2 cycles of the 8 are used to make the clock high/low, leaving 6 cycles to read the data, send it to output, decrement reg, AND goto SAMPLE. This really is a lot to do in 8 instruction cycles. :shock:

You see, I'm using the PIC16F84A with a 20MHZ clk, giving an instruction period of 200ns. For 8 cycles per sample, = 1.6uS for each bit.

Notes:
The mark/space ratio of the clock is not really important, as long as its above 20ns, (10th of a cycle).

More than 1 bit, cannot be stored, basically, I'm sending the data
out 'on-the-fly'.

The upper limit on the number of instruction cycles for retrieving a bit from the ADC is 8 (inc. subroutine calls, and return, which take 2 cycles)

I really hope someone can provide some alternatives (writing in another language?) because this is the only problem I have with my project, is this is solved, its plain sailing from here on. :p

Blueteeth, (email: paranoidfoo@hotmail.com)
 
You can certainly read a 'bit' by reading the entire byte with 'movf PortB, w', and write it out PortA with 'movwf PortA' - but bear in mind the 7 outputs on PortB will be read as well - and written to PortA.

What exactly are you trying to do?, and what ADC are you using?.
 
thanks for the reply

What am I trying to do?

I'm trying to make a wireless guitar system, using a standard SAR 16-bit adc, sampling at around 25-35khz. Seeing as the output from the adc is serial, I thouhgt it would be easier to use that output simply connected to the radio TX, all I want the PIC to do is add start/stop bits and control the ADC. three outputs are needed, CLOCK and CS for the ADC, and the main output which is transmitted. The only input I have is from the ADC.
The reason I wanted to use the PIC was because I'm OK at programming in assembly, I've got a programmer and its cheap, making it easier to experiment with. However, I could always go down the PLD route.

About the ADC, does anyone think that a sigma-delta converter would be better??

If I move the entire byte from portB to portA (or visa-versa) that would do the job, but I'm still worried if it would actually do it. Remember, the port I'm 'copying' contains 2 outputs and 1 input, so when I copy that byte from the port, would the other port contain those 3 signals? (inculding the input) It would suit me fine, seeing as I only need the output for the transmitter from portA, the other two would be redundent.

One other thing, while I'm posting I might as well include other questions,
Does anyone know what the best way to recieve serial data? I'm currently looking into tri-polling and clock recovery so I won't need a super fast clock for the reciever.

And if anyone has any links on wireless digital audio. I'd really apreciate it, I've got about 200MB of pdf files from my research, but I'm still not sure how to do it.

Thankyou :lol:

Scott
 
Readng from a port does not change the state of the outputs. A BTFSS PORT instruction has the same effect on the port as a MOVF PORT,W.

Try this code. The bit position of the ADC output (input in the PIC) should be the same as the RF TMTR input (output in the PIC). No other output should be on PORTA or its state will depend on the corresponding bit in PORTB.

Code:
SAMPLE:
   BSF       PORTB,1      ;make clock high 
   MOVF      PORTB,W      ;read the data input and store it in W  
   MOVWF     PORTA       ;send the data bit to output
   NOP                         ;wasted cycle, to equal m/s ratio of clock. 
   BCF       PORTB,1      ;make clock low 
   DECFSZ    Count,F    ;count = 16 for  the sub' to run 16 times, dec count 
   GOTO      SAMPLE       ; if count is non-zero take another sample 
   RETURN
 
Re: thanks for the reply

Blueteeth said:
What am I trying to do?

I'm trying to make a wireless guitar system, using a standard SAR 16-bit adc, sampling at around 25-35khz. Seeing as the output from the adc is serial, I thouhgt it would be easier to use that output simply connected to the radio TX, all I want the PIC to do is add start/stop bits and control the ADC. three outputs are needed, CLOCK and CS for the ADC, and the main output which is transmitted. The only input I have is from the ADC.
The reason I wanted to use the PIC was because I'm OK at programming in assembly, I've got a programmer and its cheap, making it easier to experiment with. However, I could always go down the PLD route.

About the ADC, does anyone think that a sigma-delta converter would be better??

If I move the entire byte from portB to portA (or visa-versa) that would do the job, but I'm still worried if it would actually do it. Remember, the port I'm 'copying' contains 2 outputs and 1 input, so when I copy that byte from the port, would the other port contain those 3 signals? (inculding the input) It would suit me fine, seeing as I only need the output for the transmitter from portA, the other two would be redundent.

Yes, it would contain everything from the port you read, as long as the other pins on the destination port aren't been used it won't cause any problems.

My biggest concern is your radio link - what are you using?, what frequency is it?, and what bandwidth?. If you are reading 35,000 16 bit samples per second, that's 70,000 bytes per second - 700,000 baud over a serial link. Then you need to add error correction, except you don't have the processor power to do it - but that would probably double the serial requirements - 1,400,000 baud. The normal small licence free UHF transmitters can normally manage 2400 baud - a slight increase in bandwidth looks to be required :lol:

If this for a university project?, there doesn't seem much advantage attempting a digital system when there are plenty of effective analogue systems available.
 
thanks for the answers...

Hey, I finally managed to finish the code, I abandoned the subroutine and wrote it out in full. That way, I don't have to worry about the two cycles used to call and return from the code. The PIC uses 6 instruction cycles for each bit sent. With a 20Mhz clock thats 6*200ns = 1.2us per bit.
This roughy equates to 833.3kbs. Since the data is sent and recieved 'on-the-fly', no error correction will be employed, I'm not planning to store any data to keep the delay between the sample and the output at the reciever at a minimum. Also, this allows 'tri-poling' to be used at the reciever (or I might just manchester encode it) because with 6 instructions for each bit, the reciever can pole the input using 2 instructions.

About the radio link, UHF transmitters are way to slow and basic, I'm building a 2.4GHz DSSS system from scratch, saying that, it probably won't comply with regulations because I really can't be bothered using BPSK, instead, GMFSK should be a bit easier.

One more question :lol: The DAC I've got only accepts BTC data, not straight binary. If anyone knows how I can convert standard 16-bit data to this I would be grateful, although, I don't think a PIC can do it fast enough, but the reciever can be as big (physically) and as complicated as I want, so PLD's might have to be employed. Dispite my electronics BSc, I'm no too familiar with the BTC format. It seems to me that the MSB determinds whether the signal the DAC outputs is positive or negative, the other 15 bits simply determine the magnitude of the signal.

Thankyou all for your advice and patience, especially Ivancho who basically guided me through the first steps of this design.

Scott (aka Blueteeth) :shock:
 
Status
Not open for further replies.

Latest threads

New Articles From Microcontroller Tips

Back
Top