NEW: Learning electronics? Ask your questions on the new Electronics Questions & Answers site hosted by CircuitLab.
Microcontroller Programming » Serial setup for wireless transmission
August 03, 2010 by lsoltmann |
I recently got the CY2196R transceivers that many people on this forum have gotten for wireless transmission. I'm planning on using them to build a wireless telemetry system for aircraft. I'm new to C programming and microcontrollers so this is probably a daunting task for a newbie but I thought I would give it a shot. I have read through the USART stuff in the ATMega168 data sheet but am still having trouble setting it up. I was wondering if anyone could push me in the right direction. In the code below, the UCSRnA ,UDREn, and UDRn registers are undeclared when I try to compile. Do I need to declare these? or am I going about all of this the wrong way? The transceivers require the baud rate to be 19200.
|
---|---|
August 03, 2010 by mongo |
I have a pair of those as well... Never got them to talk. I found a blog page that has some interesting info. Here it is: I am going to give it one more try myself before writing the whole thing off. |
August 04, 2010 by lsoltmann |
I've read the blog before and the hardware side I don't have a problem with ... its the software side. I wrote the code above to be a simple test to see if I could transmit the word "test" from one MCU to the other. Not knowing that much about C programming I don't know why I can't compile the above code. |
August 04, 2010 by hevans (NerdKits Staff) |
Hi lsoltmann, There are a couple of issues with your code that I see. Strings in C are a bit difficult to deal with, and I think are at the root of the problem. To simplify things, lets focus on sending a single character which is 8 bits, and is what the USART transmits at a time anyway. In both your functions you need to define the type for your inputs. C is a typed language, so every variable needs to be told what its type is when being defined.
In your main loop you can send one character:
This will get your code to compile. I think you will still need to look into the initialization you are doing a bit more. Right now it is set to 2 stop bits, which depending on your setup might not be what you want. If you take a look at uart.h in the libnerdkits folder you will see the way we initialize the UART. Hope that helps. Humberto |
August 06, 2010 by lsoltmann |
I made the changes that you suggested but it still did not compile. I decided to abandon this route and look back at the tempsensor project as I remember seeing code in there for serial output to the computer. I rewrote the above code following the code used by the tempsensor project and was able to get the CY2196R to talk to the computer. The code that ended up working was this
Pretty simple piece of code but I figure I would post it for those that might be having trouble like me. I had the serial cable plugged directly from the computer to the other CY2196R module and had to use this line in the terminal (I'm on a Mac) to see the serial port. screen /dev/tty.PL2303-0000101D 19200 I found this from the webiste http://www.tigoe.net/pcomp/resources/archives/avr/000749.shtml Now that I've got the MCU talking wirelessly, time to get started with the telemetry system project! |
August 06, 2010 by Ralphxyz |
Where can I get the CY2196R and Transmitter? Or similar wireless modules. Everything I see on the web is in Chinese is there a usable datasheet the Google translations are lacking at best. Ralph |
August 06, 2010 by lsoltmann |
The CY2196R is a transceiver so it does both Tx and Rx. I got them from http://www.sureelectronics.net/goods.php?id=379 It says GP-GC010 but they shipped me the CY2196R ... according to a google search, this has happened to everyone. The translated data sheet I got from http://www.zonemikel.com/wordpress/?p=535 which also has a good discussion on setup and use. |
September 21, 2010 by lsoltmann |
So I've got most of the telemetry system done, but am having trouble with the receiving end of the system. I read in the tractor sled pull forum on this site about sending and receiving serial over the wireless modules. After completing all the required math, I'm sending the data to the lcd screen wirelessly using the following code
On the receiving end I'm using
to get the data. The data is displaying correctly except that it is not in the correct order. The "tas_mph" variable that I sent does not seem to be written to "&tas_mph" since on the screen the values are not in the right order. The code on the receiving end looks like this.
So to summarize the problem ... the battery voltage is showing up on the airspeed line, the airspeed on the altitude line, temperature on the battery voltage line, and altitude in the temperature line. Does anyone know why the order is not the same as what I sent and how to get the sent data to remain in a certain order? Thanks! |
September 21, 2010 by mrobbins (NerdKits Staff) |
Hi lsoltmann, Sounds like you're very close! Based on your description and code, I think you were trying to send in this order:
but seeing it as though the bytes were received in this order
This is just the original shifted over by one position. If you take a look at the avr-libc documentation for scanf, you'll see that it says, "The format string fmt is scanned for conversion specifications. Anything that doesn't comprise a conversion specification is taken as text that is matched literally against the input. White space in the format string will match any white space in the data (including none), all other characters match only itself. Processing is aborted as soon as the data and format string no longer match, or there is an error or end-of-file condition on stream." So ultimately, I believe that the scanf_P function isn't "looking" for the n newline as you'd like it to. Instead, it's just getting started in one position and is then taking every whitespace (including newlines) as equivalent. Can you try changing your code on the receiving side to look more like:
I've made only two changes to your original code. First, I've added the block at the start that looks for a newline character before passing off control to your main loop. That way, the receiver starts at the right position (just after a newline). Second, I've removed the "n" from the scanf_P format string, because I think it is not useful in that position and you actually want it to fail to match against the newline character. You may want to do something more advanced in case there is the possibility of mistransmission or restarting communication while the receiver is still running. However, I think this simple example will get you going for now! Let me know if that works. Mike |
September 22, 2010 by lsoltmann |
That worked ... but only for the first time that the transmitter was turned on. If I leave the receiver module turned on, and turn off and on the transmitter (simulating no signal), the display shows the voltage in the airspeed, airspeed in the altitude, temp in the voltage, and altitude in the voltage, ie. back to the same problem. You did write a small warning at the bottom of your reply about the changing the code to handle mistransmissions or temporary signal loss. Still being new to c programming, I'm not sure how to go about doing this. Thanks for you help though, much appreciated! Lars |
September 23, 2010 by mrobbins (NerdKits Staff) |
Hi Lars, I think something like this might do what you want: Change the printing code on the transmitter side to add the letter X before its sequence of lines:
Then, on the reader side, add something just before the scanf_P line that looks for the X character. (We can now omit that check for the newline.)
Now, if the transmission is interrupted (error during transmission, or the transmitter is turned off and restarted), then the receiver will just sit around waiting for the next X. Give that a try and let me know if it works! Mike |
September 27, 2010 by oldictguy |
The beauty of using uart_read() to check for a 'control character' is that it also makes scanf non-blocking. I have a similar approach in my project. I use the WIZ610wi module for serial - TCP transmissions to send POST data to a webserver. @Mike; if the transmitter gets turned off during transmission, will scanf block and simply wait for the remaining data? Is there some kind of inherent 'timeout' feature? |
September 28, 2010 by hevans (NerdKits Staff) |
Hi olddictguy, There is no way to time out a call to scanf. It will block until it receives another character to match (or not match) against the format string. However as soon as the transmitter comes back on scanf will get the X and not match it against its format string. This will cause the if statement to fail and it will loop back around to wait for the next X. You are correct that using a lower level read function to read a character from UART would give you the ability to time out if you wanted to. Note however that the uart_read() we have in the NerdKits library (uart.c in libnerdkits) waits in a busy loop until it gets a new character, essentially making it a blocking call. There are ways to write interrupt driven uart loops if you feel the need for non-blocking uart excitement! Humberto |
April 06, 2011 by Schrat |
Lsoltmann, Your problem seems similar to what I was encountering. See http://www.nerdkits.com/forum/thread/1471/ |
Please log in to post a reply.
Did you know that sound travels via pressure waves in the air, and you can make these with a piezoelectric buzzer? Learn more...
|