Need Help with Arduino Uno Sketch to Create ASCII Characters - Page 1
Forum section: electronics / general

author: Electro Fan
author_rank: Super Contributor
timestamp: April 01, 2014, 01:49:43 am
content: Hi,I'm using an Arduino Uno as a pulse generator to create some ASCII characters which are outputted from the Uno to an oscilloscope that in turn decodes the square waves as specific ASCII characters.In the sketch below I can make a series of pulses that the scope decodes as capital U characters but this is just because it is a repeating square wave. I think I might need to account for a start bit sequence or something else but I can't quite figure out what I'm missing.// Pin 13 has an LED connected on most Arduino boards.// give it a name:int led = 13;// the setup routine runs once when you press reset:void setup() {// initialize the digital pin as an output.pinMode(led, OUTPUT);}// the loop routine runs over and over again forever:void loop() {digitalWrite(led, LOW); // turn the LED off by making the voltage LOWdelay(5); // wait for a seconddigitalWrite(led, HIGH); // turn the LED on (HIGH is the voltage level)delay(5); // wait for a seconddigitalWrite(led, LOW); // turn the LED off by making the voltage LOWdelay(5); // wait for a seconddigitalWrite(led, HIGH); // turn the LED on (HIGH is the voltage level)delay(5); // wait for a seconddigitalWrite(led, LOW); // turn the LED off by making the voltage LOWdelay(5); // wait for a seconddigitalWrite(led, HIGH); // turn the LED on (HIGH is the voltage level)delay(5); // wait for a seconddigitalWrite(led, LOW); // turn the LED off by making the voltage LOWdelay(5); // wait for a seconddigitalWrite(led, HIGH); // turn the LED on (HIGH is the voltage level)delay(5); // wait for a second}Any suggestions on how I can adjust the sketch to generate specific ASCII characters with the UNO?Thanks!

author: David_AVD
author_rank: Super Contributor
timestamp: April 01, 2014, 02:06:40 am
content: So you're trying to "write text" to the oscilloscope ?The posted code is simply toggling the LED on and off.

author: mariush
author_rank: Super Contributor
timestamp: April 01, 2014, 02:19:12 am
content: I think he's trying to send BITS (1 or 0 ) and have the oscilloscope decode these bits into a series of 1 and 0.There are normally two wires used to transmit data, because one wire acts as a "clock", meaning whenever there's a "tick" on this wire, the device at the end of the wires knows there's updated data on the other wire. This way, the delay between new bits on the data wire can vary and the device will only read the new bit when it detects a tick on the clock wire.With just one wire, you have to agree on a sort of start sequence which will tell you a new sequence of bits is going to be transmitted. This can be something as simple as going LOW for 10 ms and then going HIGH for 5 ms (001 or 110) - as soon as you see that on the oscilloscope, you know your product should set a series of bits.Some devices like remote controls by their nature use a "1 wire" protocol.. basically sending a series of pulses through the air. There's several protocols but most remote controls use a very common one.Dave actually did a video about such remote controls and reading the data on Arduino and oscilloscopes, have a look :

author: Hideki
author_rank: Frequent Contributor
timestamp: April 01, 2014, 02:36:27 am
content: Electro Fan, you describe a lot of the details, show us a program, but completely and uttery miss the most important thing: What protocol do you want use?Assming it's a single serial UART line, and typical 8N1, then you need to send _ten_ bits at a time. First a start bit (always LOW), then eight data bits, which can be whatever you like, and last, but no less important, you send the stop bit (always HIGH).

author: Electro Fan
author_rank: Super Contributor
timestamp: April 01, 2014, 03:41:16 am
content: Sorry, I should have pointed out that I'm just emulating a RS232 port card (UART) protocol.I revised the Arduino sketch to add the start bit (always LOW) and stop bit (always HIGH) - thanks Hideki.// Pin 13 has an LED connected on most Arduino boards.// give it a name:int led = 13;// the setup routine runs once when you press reset:void setup() {// initialize the digital pin as an output.pinMode(led, OUTPUT);}// the loop routine runs over and over again forever:void loop() {digitalWrite(led, LOW); // turn the LED off by making the voltage LOWdelay(5); // wait for a seconddigitalWrite(led, LOW); // turn the LED off by making the voltage LOWdelay(5); // wait for a seconddigitalWrite(led, HIGH); // turn the LED on (HIGH is the voltage level)delay(5); // wait for a seconddigitalWrite(led, LOW); // turn the LED off by making the voltage LOWdelay(5); // wait for a seconddigitalWrite(led, HIGH); // turn the LED on (HIGH is the voltage level)delay(5); // wait for a seconddigitalWrite(led, LOW); // turn the LED off by making the voltage LOWdelay(5); // wait for a seconddigitalWrite(led, HIGH); // turn the LED on (HIGH is the voltage level)delay(5); // wait for a seconddigitalWrite(led, LOW); // turn the LED off by making the voltage LOWdelay(5); // wait for a seconddigitalWrite(led, HIGH); // turn the LED on (HIGH is the voltage level)delay(5); // wait for a seconddigitalWrite(led, HIGH); // turn the LED on (HIGH is the voltage level)delay(5); // wait for a second}Looks like we are now rocking and rolling. Using the sketch seems to allow the ability to create specific ASCII characters. Thanks for the help - much appreciated! EFPS, New Question: why does the counter show 83.2Hz and 78.8Hz in the two samples when the frequency shows 100 Hz? Thanks

author: hamster_nz
author_rank: Super Contributor
timestamp: April 01, 2014, 03:47:34 am
content: Quote from: Electro Fan on April 01, 2014, 01:49:43 amHere's the "loop()" code for 8 bits, one stop bit, idle state of "high", sending LSB first. I actually run it up, but it "verifies" in the Arduino GUI:Code:static char message[] = "hi there!";// the loop routine runs over and over again forever:void loop() {int a;// Some Idle timedigitalWrite(led, HIGH);delay(5); // wait for a seconddelay(5); // wait for a secondfor(a = 0; a < sizeof(message); a++){// start bitdigitalWrite(led, LOW); // turn the LED off by making the voltage LOWdelay(5);// LSB Bit 0digitalWrite(led, (message & 1) ? HIGH : LOW);delay(5);// Bit 1digitalWrite(led, (message & 2) ? HIGH : LOW);delay(5);// Bit 2digitalWrite(led, (message & 4) ? HIGH : LOW);delay(5);// Bit 3digitalWrite(led, (message & 8) ? HIGH : LOW);delay(5);// Bit 4digitalWrite(led, (message & 0x10) ? HIGH : LOW);delay(5);// Bit 5digitalWrite(led, (message & 0x20) ? HIGH : LOW);delay(5);// Bit 6digitalWrite(led, (message & 0x40) ? HIGH : LOW);delay(5);// Bit 7digitalWrite(led, (message & 0x80) ? HIGH : LOW);delay(5);// stop bitdigitalWrite(led, HIGH); // turn the LED off by making the voltage LOWdelay(5);}}You want to change "delay(5)" to be whatever your per-bit time is (e.g. 1/9600th of a second for 9600 baud).

author: Electro Fan
author_rank: Super Contributor
timestamp: April 02, 2014, 02:16:48 am
content: Quote from: hamster_nz on April 01, 2014, 03:47:34 am

author: hamster_nz
author_rank: Super Contributor
timestamp: April 02, 2014, 02:53:55 am
content: I understand what you are saying, but just can't get it in a useful context where I can give you a direct answer, so here's some background.To decode RS232 running at 'n' bits per second most hardware over-samples the incoming data line at maybe 4n.When the falling edge which is the the 'start' bit is seen (ie the last two samples were "1" for the oldest, and "0" for the most recent) the receiver assumes that the next sample is synched close enough to the center of a bit to be valid.It will then take every 4th sample as being a valid data bit, up to and including the stop bit.So over the 10 bits for each byte the receiver can drift about a quarter of a bit-time out of sync with the sender before an error will occur (assuming no noise and so on), or about 2.5% -Because one end can be running fast and the other can be slow your timing should be within 1.25% for reliable operation.300 Buad needs 3.33ms per bit, +/- about 0.04 ms.9600 Baud needs 104us per bit, +/- about 1usThe upshot is that bit-bashing RS232 at high speed is not every easy - you are best off using a hardware UART.Mike

author: Electro Fan
author_rank: Super Contributor
timestamp: April 02, 2014, 03:01:18 am
content: Quote from: hamster_nz on April 02, 2014, 02:53:55 amThanks - I am studying your reply and trying to absorb it. I sense that some type of drift is occurring. I'm going to experiment with a few variables and see if I can find some sort of pattern as to what causes what.Setting aside baud rate, any thoughts on why the counter and the frequency measurement on the scope don't seem to agree? Sometimes they are close (within 1% or so) and sometimes they are off by 2x. Is this a combination of drift (1%) and sampling issues (2x) also? Thanks again

author: David_AVD
author_rank: Super Contributor
timestamp: April 02, 2014, 03:37:18 am
content: Using delay routines in an Arduino sketch to do comms timing is not likely to yield a useful result. If you want to send serial data, use the UART hardware.

author: Electro Fan
author_rank: Super Contributor
timestamp: April 02, 2014, 03:52:10 am
content: Quote from: David_AVD on April 02, 2014, 03:37:18 ameh, the UART hardware...? is that a reference to a feature built into the Uno or a shield or something else? ThxUpdate:perhaps this is what you were suggesting:Used for communication between the Arduino board and a computer or other devices. All Arduino boards have at least one serial port (also known as a UART or USART): Serial. It communicates on digital pins 0 (RX) and 1 (TX) as well as with the computer via USB. Thus, if you use these functions, you cannot also use pins 0 and 1 for digital input or output.

author: hamster_nz
author_rank: Super Contributor
timestamp: April 02, 2014, 03:56:07 am
content: Arduinos have a built in UART - Have a look at Examples/Communicaitons/ASCII table in the Arduino GUI.You can monitor over either the host port or this over pins D0 (RX) and D1 (TX).

author: psycho0815
author_rank: Regular Contributor
timestamp: April 02, 2014, 09:02:06 am
content: You should generally use the hardware uart if possible. If that's not an option you could also use the Arduinos SoftwareSerial Library. If you insist on doing it yourself that's also were i would start. have a look at the library see how they do things. No need to reinvent the wheel.One more general thing: clean up your code. it looks like you based it on the basic blink sketch and just copy and pasted some stuff including the comments, which no longer fit what is happening in your code. Now i realise that this is just some experimental code, but that sort of thing can really come back to bite you so you should just try to get used to doing it right from the start. In this particular case, i would actually go ahead and just delete most of the comments, since they add absolutely no information to you code.

author: dannyf
author_rank: Super Contributor
timestamp: April 02, 2014, 10:55:30 am
content: That's pretty simple, isn't it?Code://send a char's ascii bit form//msb first//pin idles high#define ASCII_PIN 2 //ascii pin#define ASCII_DLY 5 //delay between bitsvoid ascii_putc(unsigned char dat) {unsigned char mask = 0x80; //mask of bits to be sent, msb first//send start bit(s) here//send the ascii chardo {if (dat & mask) digitalWrite(ASCII_PIN, HIGH); //send '1'else digitalWrite(ASCII_PIN, LOW); //send '0'mask = mask >> 1; //shift to the next bitdelay(ASCII_DLY); //waste some time} while (mask); //till all bits are sent//send stop bit(s) heredigitalWrite(ASCII_PIN, HIGH); //ascii_pin idles high}You can then write a routine to send a stringCode://send a stringvoid ascii_puts(unsigned char * str) {while (*str) ascii_putc(*str++);}And your user code would be something likeCode:ascii_putc('U'); //send 'U'ascii_puts(aBuffer); //send a string in aBuffer...Learn a little bit C would be quite helpful to you.

author: Electro Fan
author_rank: Super Contributor
timestamp: April 03, 2014, 03:27:10 am
content: Quote from: Hideki on April 01, 2014, 02:36:27 amHideki, hamster_NZ, and everyone, thank you for your patience and help.I have attempted to clean up the comments as psycho0815 suggested.Below is a sketch that produces aCapital A ASCII characterwith the decoder. The decoderdisplays the bits in Binary as 01000001(this is how the bits are rendered from left to right on the scope screen with the decoder set to LSB).I could be mistaken but the Start bit is not only the starting bit but it is also the first data bit. That leaves the next seven bits as the remaining bits in an eight bit byte. Clearly, this sequence produces the Capital A as expected based on the ASCII table. This leaves two more bits (bit #9 is a 1 (LOW) - which I'm not sure of, and bit #10 which is a 0 (HIGH), which presumably is the Stop bit.So, this conforms pretty closely to what you (Hideki) prescribed in your post (the first bit is the LOW start bit and the last bit is the HIGH Stop bit, and there are 8 data bits (including the Start bit), but what is the 9th bit? I am guessing that it could be a Parity bit - I have my scope set to "None" for parity which conforms to your 8N1.Also, is the 8th bit (as shown in the sketch below) the MSB (Most Significant Bit)?Comments? Thanks!/*ASCII Generator, Create Capital A*/// Pin 13 has an LED connected on the Arduino board.// give it a name:int led = 13;// the setup routine runs once when you press reset:void setup() {// initialize the digital pin as an output.pinMode(led, OUTPUT);}// the loop routine runs over and over again forever:void loop() {digitalWrite(led, LOW); // make the voltage LOW (turn the voltage off) 1 = Start bitdelay(1); // wait for a seconddigitalWrite(led, HIGH); // make the voltage HIGH (turn the LED on) 0delay(1); // wait for a seconddigitalWrite(led, HIGH); // make the voltage HIGH (turn the LED on) 0delay(1); // wait for a seconddigitalWrite(led, HIGH); // make the voltage HIGH (turn the LED on) 0delay(1); // wait for a seconddigitalWrite(led, HIGH); // make the voltage HIGH (turn the LED on) 0delay(1); // wait for a seconddigitalWrite(led, HIGH); // make the voltage HIGH (turn the LED on) 0delay(1); // wait for a seconddigitalWrite(led, LOW); // make the voltage LOW (turn the voltage off) 1delay(1); // wait for a seconddigitalWrite(led, HIGH); // make the voltage HIGH (turn the LED on) 0 = MSB?delay(1); // wait for a seconddigitalWrite(led, LOW); // make the voltage LOW (turn the voltage off) 1 = Parity bit?delay(1); // wait for a seconddigitalWrite(led, HIGH); // make the voltage HIGH (turn the LED on) 0 = Stop bitdelay(1); // wait for a second}

author: Electro Fan
author_rank: Super Contributor
timestamp: April 03, 2014, 04:36:31 am
content: Quote from: Hideki on April 01, 2014, 02:36:27 amHideki, here is another sketch. This one is for aCapital B ASCII character. You can see that the binary code is 01000010.It would seem that the Start bit is now a 0 which is a HIGH. I probably have something goofed up, but this seems to be at odds with the notion that the Start bit is always LOW. Thanks, EF(It seems that the Start bit is also the LSB (Least Significant Bit) as simply incrementing up from the 01 to 10 end of the byte toggles the code from A (as shown in the previous post) to B (as shown below). Yes/No? Thanks)/*ASCII Generator, Create Capital B*/// Pin 13 has an LED connected on the Arduino board.// give it a name:int led = 13;// the setup routine runs once when you press reset:void setup() {// initialize the digital pin as an output.pinMode(led, OUTPUT);}// the loop routine runs over and over again forever:void loop() {digitalWrite(led, HIGH); // make the voltage HIGH (turn the LED on) 0 = Start bit = LSB?delay(1); // wait for a seconddigitalWrite(led, LOW); // make the voltage LOW (turn the LED off) 1delay(1); // wait for a seconddigitalWrite(led, HIGH); // make the voltage HIGH (turn the LED on) 0delay(1); // wait for a seconddigitalWrite(led, HIGH); // make the voltage HIGH (turn the LED on) 0delay(1); // wait for a seconddigitalWrite(led, HIGH); // make the voltage HIGH (turn the LED on) 0delay(1); // wait for a seconddigitalWrite(led, HIGH); // make the voltage HIGH (turn the LED on) 0delay(1); // wait for a seconddigitalWrite(led, LOW); // make the voltage LOW (turn the LED off) 1delay(1); // wait for a seconddigitalWrite(led, HIGH); // make the voltage HIGH (turn the LED on) 0 = also MSB?delay(1); // wait for a seconddigitalWrite(led, LOW); // make the voltage LOW (turn the LED off) 1 = Parity bit?delay(1); // wait for a seconddigitalWrite(led, HIGH); // make the voltage HIGH (turn the LED on) 0 = Stop bitdelay(1); // wait for a second}

author: Dago
author_rank: Frequent Contributor
timestamp: April 03, 2014, 06:43:50 am
content: You should be using the UART for this kind of serial communication. You can do it in software but there's no point if you have an UART.

author: psycho0815
author_rank: Regular Contributor
timestamp: April 03, 2014, 08:27:28 am
content: Have a look at the UART spec. the stop bit is suppossed to be a logic high i.e. 0 V.I edited you comments to reflect what you're actually sending.Code:// the loop routine runs over and over again forever:void loop() {digitalWrite(led, HIGH); // make the voltage HIGH (logic 0) = LSBdelay(1);digitalWrite(led, LOW); // make the voltage LOW (logic 1)delay(1);digitalWrite(led, HIGH); // make the voltage HIGH (logic 0)delay(1);digitalWrite(led, HIGH); // make the voltage HIGH (logic 0)delay(1);digitalWrite(led, HIGH); // make the voltage HIGH (logic 0)delay(1);digitalWrite(led, HIGH); // make the voltage HIGH (logic 0)delay(1);digitalWrite(led, LOW); // make the voltage LOW (logic 1)delay(1);digitalWrite(led, HIGH); // make the voltage HIGH (logic 0) MSBdelay(1);digitalWrite(led, LOW); // make the voltage LOW (logic 1) stop bitdelay(1);digitalWrite(led, HIGH); // make the voltage HIGH (logic 0) = Start bitdelay(1);}The reason your scope can decode that is probably mostly luck and some clever logic in your scope

author: David_AVD
author_rank: Super Contributor
timestamp: April 03, 2014, 09:35:44 am
content: For typical async comms, the format is 8N1. This means 8 data bits, no parity bits and 1 stop bit. There is also the start bit at .. well... the start !So, that's 10 bits all up. (1 start bit, 8 data bits and 1 stop bit) Unless you get this right, you won't get any sense when decoding it.

author: Hideki
author_rank: Frequent Contributor
timestamp: April 03, 2014, 01:57:29 pm
content: This really isn't as hard as you're trying to make it be1. The signal is assumed to idle at HIGH when no data is being sent. You have to start out with this condition, or everything below will fail. Do this in setup and not inside the loop. One thing to watch out for is that you may have to actually let it stay HIGH a little while before you start sending anything, or the receiver may miss the first start bit (it actually looks for the signal going from HIGH to LOW).2. The first thing you do when you want to send a byte is to send the start bit... at the start! That makes sense, doesn't it?Since the start bit is LOW, the receiver will detect this HIGH to LOW transition and get ready for receiving your new byte.3. Then you send your 8 bits. The standard for UART is the Least Significant Bit first, so you send bit 0 to bit 7 in order.4. After all 8 bits the byte is done and you send a stop bit. This bit is always HIGH.After the stop bit is done you have sent 10 bits in total, and we are back at the initial state from step 1. The signal is HIGH, and you can stay that way forever, or immediately send another byte by going to step 2.psycho0815: Please don't confuse everyone by saying that logic high is 0 V. That isn't even true for RS-232, which uses different signal levels than plain UART from an arduino output.

author: Electro Fan
author_rank: Super Contributor
timestamp: April 12, 2014, 09:39:54 pm
content: Hi EEVers, Thanks for the previous advice.I'm thinking about approaching my ASCII generating/decoding experiments with a different set of test tools other than the Uno.Just checking to see if you have any thoughts on the utility of a few options.The goal is to have the ability to generate test signals that are effectively ASCII characters while having control over the amplitude and pulse durations and maybe the underlying clock frequency on which the pulses ride.So, here are the possibilities:1. Rigol 832 DC Programmable Power Supply - not sure if it will provide enough control from the front panel or probably better yet from a PC to generate start bits, data bits, and stop bits. Seems like this should be doable, but maybe at a fixed "clock" frequency. Probably overkill for just this experiment but it would of course be a good DC power supply for lots of other uses. (An additional concern is whether the various feature issues that surfaced during Dave's testing have been sufficiently resolved.) My guess is that this won't be the best of the 3 options.http://eu.rigol.com/download/Oversea/DP/User_guide/DP800_UserGuide_EN.pdf2. Rigol DG4062 Arbitrary Waveform GeneratorWhile this seems to offer the ability to generate arbitrary waveforms it isn't clear from reading the manual whether this will provide sufficient flexibility to generate ASCII characters, but maybe... (Also overkill for this experiment, but hey, who wouldn't want a reason to own a nice arb generator?)www.tequipment.net/assets/1/26/Documents/Rigol/DG4062/dg4062_doc_3.pdf3. USBee-SX Logic Analyzer with built-in Signal GeneratorThis seems to have some limitations in terms of voltage levels but might have the best flexibility and ease of use for creating bit patterns. This option is the least expensive of the three and would provide a Logic Analyzer as a bonus.http://www.usbee.com/sx.htmlhttp://www.usbee.com/sx.html#SignalOr maybe there are better ways to accomplish the goal?Thanks!

author: dannyf
author_rank: Super Contributor
timestamp: April 13, 2014, 11:18:29 am
content: QuoteYeah. Like knowing what you are trying to accomplish, planning out your tasks ahead of time and possessing the necessary skills to get it done.

author: Electro Fan
author_rank: Super Contributor
timestamp: April 13, 2014, 02:10:01 pm
content: Quote from: dannyf on April 13, 2014, 11:18:29 amSounds a little condescending but maybe I'm just reading that into your reply.As mentioned above:The goal is to have the ability to generate test signals that are effectively ASCII characters while having control over the amplitude and pulse durations and maybe the underlying clock frequency on which the pulses ride.Let us know if you have any comments on the three options presented or any helpful suggestions, or if you want to take some other shots.

author: SL4P
author_rank: Super Contributor
timestamp: April 13, 2014, 02:19:03 pm
content: If you actually know what you're doing in the hardware and software domains, including the requirement for variable bit amplitude etc, then to achieve what you want in code is going to be tricky but not impossible, while maintaining the sharp rise and fall times of the tx data.Use the UART or software bit-bashing on a CPU with as fast a clock as you can get (gives you more time to do things *between* tx bits). Hook up whichever TX pin you use back to an interrupt on change .Put a variable gain amp on the outbound TX data, amplitude driven from another port.Then you can use the interrupt to identify when each bit has been sent (interrupt on change), and you can ramp or modify the slew rate in between each bit.If you want to vary the bit timing - you may be able to fiddle the TX clock divisor, or use software bit-bashing to manage each bit like you are already.It ain't going to be a walk in the park - but I think it's possible - and quite interesting to consider !

author: Electro Fan
author_rank: Super Contributor
timestamp: April 13, 2014, 03:11:05 pm
content: Quote from: SL4P on April 13, 2014, 02:19:03 pmOk, I’m starting to think this is going to be more difficult than I had expected. Not sure exactly why yet, but I’m getting the message.Clearly, given my very beginning skills the Arduino didn’t give me enough control over something – I suspect it had something to with timing but I’m not sure. Perhaps it's doable with the Arduino and I just couldn't make it happen. Without a doubt I don’t have more than very beginning software coding and super beginning hardware design skills, I get that.What I have to work with is just a basic understanding of amplitude and frequency. When I get to components I’m good to Ohm’s Law (sort of) and after that I’m in heavy figure-it-out mode. So, what I’m not trying to do is to create pulses by building a circuit board with components.The idea for this project has been to use some reasonably affordable piece of test equipment (if not the Arduino, maybe a programmable DC power supply or an Arb generator) or other tool (like the USBee Logic Analyzer that seems to double as a generator) so as to gain enough control over pulse generation to sequence out HIs and LOWs. The goal is to create the 1s and 0s patterns found on the ASCII chart so they can be captured and decoded on a scope. This lets me visually inspect the waveforms and study things. Small potatoes I realize, but interesting for a guy who is just figuring out lots of stuff from the very beginning at the hands on level.I’m coming at this backwards from most EEs I think. I use some basic test equipment to see and learn rather than to design and debug. All I want to do for now is consolidate my understanding of the relationships between analog signals and the digital data riding on (represented by) the signals. The more control I can have over amplitude, frequency, duty cycle, etc. the better. FWIW, I have a hunch that your advice about getting “a CPU with as fast a clock as you can get” is great advice. I think the Uno was very close to the right tool for what I have in mind except that I couldn’t find a way to better manage the clock and maybe the clock was too slow (not really too slow, I just couldn't control the increments with enough granularity). Just a hunch, I could be wrong.The Rigol DC programmable power supply and the Rigol arb generator would maybe not be useful for such a project? Maybe the USBee generator could do the trick?Thanks again, EF

author: Hideki
author_rank: Frequent Contributor
timestamp: April 13, 2014, 08:14:03 pm
content: You can get analog signals from the arduino too. Build a simple R2R DAC from resistors and connect it to the arduino pins. Maybe start out with two bits to get four different analog levels? All you need is four resistors.When you figure out how that works you can add more bits using more resistors. 8 bits gets you 256 different levels, which should be more than enough for testing.See for examplehttp://forum.arduino.cc/index.php?topic=150147.0As you see you need two resistors for each additional bit. One resistor being twice the value of the other. The exact values are not too critical. You can use all the same value if you like, since two in series makes double the value, or two in parallel makes half.Note: This step may be too difficult so soon, but to change all bits at once, write directly to the port, bypassing the slow digitalWrite function.Or... use the analogOut and put a lowpass filter on the pin, but this limits you to rather slow bitrates.

author: SL4P
author_rank: Super Contributor
timestamp: April 17, 2014, 02:16:11 pm
content: @Hideki - I doubt you can get the DAC performance required to manipulate the individual bits in (even a slow) serial data stream...I was initially thinking the same, but suggested the external DAC to provide real-time 'distortion' of the serial data levels as expected in the original posts.The bit-interrupt feedback also provides a tidy way of knowing when to burp & fart in order to manipulate individual bits as they pass through the gain amp.

author: Electro Fan
author_rank: Super Contributor
timestamp: April 20, 2014, 01:37:36 am
content: Ok, here is another attempt at being able to generate strings of various ASCII characters.....These HP/Agilent Pulse Generators looks like they might be able to create ASCII byte patterns by providing relatively easy control over timing, amplitude, etc. At $800 - 1700 it makes no sense for my purposes but maybe someone knows of a (considerably) less expensive device that might suffice?http://www.ebay.com/itm/HP-Agilent-8110A-Pulse-Generator-81106A-150MHz-with-81103A-Output-Card-/141081716744?pt=LH_DefaultDomain_0&hash=item20d9202808http://www.ebay.com/itm/HP-Agilent-81101A-Pulse-Generator-50-MHz-Clean-Working-with-Warranty-/261455034092?pt=LH_DefaultDomain_0&hash=item3cdfef36echttp://www.ebay.com/itm/AGILENT-81101A-PULSE-GENERATOR-/271005892346?pt=LH_DefaultDomain_0&hash=item3f1935befaNot even clear the above models will offer enough flexibility to generate strings for ASCII characters:http://cp.literature.agilent.com/litweb/pdf/5980-1215E.pdfOlder model?:http://www.ebay.com/itm/Agilent-HP-8118A-50-MHz-Dual-Channel-Pulse-Generator-/220479463459?pt=LH_DefaultDomain_0&hash=item335599a023I'm guessing the models below will not allow the variations needed to create ASCII bytes (other than maybe highly symmetrical character patterns such as a capital U), right?http://www.ebay.com/itm/Hewlett-Packard-HP-Agilent-8013B-Pulse-Generator-/360405990545?pt=LH_DefaultDomain_0&hash=item53e9defc91http://www.ebay.com/itm/HP-Agilent-8003A-Pulse-Generator-L180-/131155740155?pt=LH_DefaultDomain_0&hash=item1e897dc5fbAnd finally, it looks like for $83kthis should be doable:http://www.home.agilent.com/en/pd-1000004569%3Aepsg%3Apro-pn-81134A/pulse-pattern-generator-335-ghz-dual-channel?&cc=US&lc=engI definitely don't need 3 GHz; maybe 1 MHz would be nice.Thanks for any ideas. EF

author: dannyf
author_rank: Super Contributor
timestamp: April 20, 2014, 02:05:11 am
content: If you understand what you are trying to do, it shouldn't take more than $10 and maybe 15 minutes of programming to do it.

author: Hideki
author_rank: Frequent Contributor
timestamp: April 20, 2014, 02:10:31 am
content: You DO understand that the Arduino has hardware serial on Digital Pin 1, right? You change the timing with Serial.begin(9600) or some other speed, and send data with Serial.write(byte).If you want to change the amplitude of all the high pulses, then a simple potentiometer will do that. It costs much less than $800. A voltage divider with two resistors will do in a pinch.

author: Electro Fan
author_rank: Super Contributor
timestamp: April 20, 2014, 04:12:52 am
content: Ok, maybe I'm just a little confused (or maybe a lot confused)?At the start of the thread entitled "Need Help with Arduino Sketch to Create ASCII Characters" I posted an explanation of what I was trying to accomplish and what I had wired together (with just Pin 13 and GND) and programmed with the Uno.That resulted in various posts including some saying that perhaps it was going to be more difficult than anticipated (for example, Reply #23, concluded "It ain't going to be a walk in the park - but I think it's possible - and quite interesting to consider !" Hideki made some follow-on suggestions and SL4P raised some more questions in Reply #26).Now we have dannyf saying "if you understand what your are trying to do, it shouldn't take more than $10 and maybe 15 minutes of programming to do it." Not to make too fine of a distinction, but I think I understandwhatI'm trying to do, just nothowto do it.Anyone want to suggest whatspecificallywould be the Uno wiring diagram and thespecificcode that would enable HI and LOW pulses to be generated so as to create ASCII character strings?Thanks, EF

author: Dago
author_rank: Frequent Contributor
timestamp: April 20, 2014, 11:00:25 am
content: Quote from: Electro Fan on April 20, 2014, 04:12:52 amCode:Serial.begin(9600);Serial.println("ASCII string");That's all you need if you just use the USART... Connect whatever you want to pins 0 (RX) and 1 (TX).

author: Hideki
author_rank: Frequent Contributor
timestamp: April 20, 2014, 11:08:31 am
content: Code:void setup() {Serial.begin(9600); // 9600 bits per second}void loop() {Serial.write(65); // send this byte}Switch to pin 1 as the output instead of pin 13 and this should send 65 continously (ASCII for the letter 'A').Once you get that going you can start changing the output level to something less than 5 volts (I don't know WHY, but you seem to think this is important).

author: SL4P
author_rank: Super Contributor
timestamp: April 20, 2014, 12:31:58 pm
content: Perhaps I misread OP, but in the chain of discussion, thee was a requirement to vary bit timing and bit levels (i.e. simulate line faults).If this is not the case then yes 15, and 10 minutes will close the thread.But my lesson learned - in a forum, perhaps the question is not what it seems.Cheers, and let us know how you go.

author: Electro Fan
author_rank: Super Contributor
timestamp: April 20, 2014, 08:56:08 pm
content: Hideki, Dago, SL4P – ThanksHideki, I’ve set pin 1 (rather than 13) for output. Pin 0 (not GND) should be used for the other wire, right? (Same as suggested by Dago, right?)Thanks, EF

author: Hideki
author_rank: Frequent Contributor
timestamp: April 20, 2014, 09:09:53 pm
content: Yes, use pin 1, but you shouldn't add extra code to set it to an output. That happens automatically when calling Serial.begin.Pin 0 is RX (Receive) for sending data _into_ the Arduino from some other device. At the level you're at, you really shouldn't be trying that today.The only "other wire" you need, is GND. Connect that the the oscilloscope probe's ground clip.

author: Electro Fan
author_rank: Super Contributor
timestamp: April 20, 2014, 09:27:26 pm
content: Hideki, Thanks.Ok, for now I have just pin 1 and GND connected to the scope. Your sketch using Serial.write(65) uploads fine that way.The scope reads 5.01 volts.The scope decoder is set for 9600 and RS232.The scope is set on 8 data bits plus 1 stop bit. Parity is none. Packet is off. Packet End is Null. Polarity is Normal. Endian is LSB.At 200us I can see two full bytes on the scope display at one time.With the above settings the Binary readout is 11110101 which isn't "A".Any suggestions on some possible adjustments? Thanks again, EF

author: Hideki
author_rank: Frequent Contributor
timestamp: April 20, 2014, 09:47:51 pm
content: You're not using RS232 levels (+3 to +15 volts and -3 to -15 volts). This is normal serial UART levels of 0 and 5 volts.From the manual it looks like you can change Polarity from Negative to Positive to get around this issue.

author: Electro Fan
author_rank: Super Contributor
timestamp: April 20, 2014, 10:07:05 pm
content: Hideki,Could be some progress here.On the trigger Rigol gives the following options:Edge, Pulse, Runt, Slope, Video, Pattern, Setup/Hold, RS232, I2C, and SPII think RS232 does inform the scope to look for the +3/+15 and -3/-15 volts, but my sense is that the trigger is not that sensitive and it can determine a HI from a LOW pretty easily. (So maybe I can leave it on RS232 and just adjust the polarity?)On the decoder the Rigol gives the following options:Parallel, RS232, I2C, and SPI.I'm still playing with it but any suggestions on the combination of trigger and decoder options are welcome.Thanks! EFPS, before we go too far down any wrong paths (and one of the reasons I thought we were getting close with the analog pins) I just wanted to restate that the eventual goal is to be able to at a minimum generate bits that make strings of bytes (render words on the display, etc.) - not because I like seeing words on the display but to gain control and understand the patterns including the control characters. Ideally I'd like to be able to adjust single bits so as to adjust bytes from within into new bytes (rather than just assign values like 65). What I'd really like to be able to do is to adjust HIs and LOWs to toggle start and stop bits as well as data bits - but maybe we can save some of this for "Phase 2"Thanks again

author: David_AVD
author_rank: Super Contributor
timestamp: April 20, 2014, 10:12:57 pm
content: Is there any real world applications for what you're fiddling about with here? I understand about learning as an exercise, but I can't really work out what you're trying to learn.

author: Electro Fan
author_rank: Super Contributor
timestamp: April 20, 2014, 10:23:46 pm
content: Quote from: David_AVD on April 20, 2014, 10:12:57 pmAs mentioned in the "PS" I added above I want to be able to see exactly where each bit, including control bits such as start and stop bits end and begin and be able to control the full sequence of bits. When I can adjust bits one at a time including start and stop bits, parity bits, etc. and get the data bytes and special characters (spaces, punctuation, etc.) to reliably render without errors I will feel like I have figured it out. This will not earn a course credit much less help earn a degree in anything. It is strictly curiosity and a hobby.Net, net: I just want to be able to set, control, and generate bits and have them display predictably as waveforms and decode reliably as bytes according to the ASCII character table.

author: dannyf
author_rank: Super Contributor
timestamp: April 20, 2014, 11:06:32 pm
content: QuoteThat didn't take 15 minutes to write, right?QuoteDago's code would allow you to do precisely that.What you are trying to do is really simple, as many have pointed out to you - it cannot be simpler than this! Quite frankly, you seem to be speaking a different language here. If you find this frustrating, I would suggest that you go back and take an intro level class in electronics.Having said that, here is what I would suggest to you:1) take Dago's code and modify it slightly to make it easier for you:Code:Serial.println("A");delay(500);Every 500ms, it will send "A" (plus return and potentially null), so you can watch it on your scope.2) Take a picture of that waveform, and go check on uart protocol and make comparison.3) Once you have really understood that, go get the datasheet for your mcu and read about the usart module and compare it to how arduino did it.4) make changes to it as you need.Again, this thing is really simple and don't work too hard to make it complicated.

author: Electro Fan
author_rank: Super Contributor
timestamp: April 21, 2014, 01:04:47 am
content: dannyf (and everyone), Thanks for the continued "encouragement"Attached is a file produced with the suggested code.A few questions (some of which are probably separate from the original "goal"):1. What is causing the Line Feeds to be displayed? Something embedded in the Uno?2. What causes the occasional error characters such as the "*" and the "5"?3. The counter remains pretty stable around 3.16KHz but the frequency measurement (which shows 3.125kHz in the image) bounces around between about 2.5kHz and >5kHz. Is the frequency measurement not able to update the display as reliably/quickly as the counter?4. I'm guessing that the narrow lines at the top and bottom of the square waves are something that might be cleaned up with a better ground connection? (They clean up if I insert a 50 Ohm terminator between the test leads and the scope - as shown in the bottom photo.)Thanks, EF

author: dannyf
author_rank: Super Contributor
timestamp: April 21, 2014, 01:23:26 am
content: Let me just repeat what I said earlier: you should take an intro level class at any decent colleges. It will get you where you want to go a lot faster.QuoteThat measurement depends on the baud rate and the content being transmitted.

author: Electro Fan
author_rank: Super Contributor
timestamp: April 21, 2014, 01:25:47 am
content: Having fun now (getting predictable results). Thx for all the help!

author: Electro Fan
author_rank: Super Contributor
timestamp: April 21, 2014, 01:28:51 am
content: Quote from: dannyf on April 21, 2014, 01:23:26 amYep, I get it about the class - if I just didn't have a day jobIn the meantime (I know what you guys are thinking) this the classroomI get the notion of the baud rate.... why does the frequency measurement not give the same result as the counter? Thanks

author: retrolefty
author_rank: Super Contributor
timestamp: April 21, 2014, 01:35:58 am
content: Quote

author: Electro Fan
author_rank: Super Contributor
timestamp: April 21, 2014, 02:06:21 am
content: Quote from: retrolefty on April 21, 2014, 01:35:58 am

author: SL4P
author_rank: Super Contributor
timestamp: April 21, 2014, 04:09:33 am
content: Quote from: dannyf on April 20, 2014, 11:06:32 pm

author: SL4P
author_rank: Super Contributor
timestamp: April 21, 2014, 04:14:09 am
content: What happened to...Quote from: Electro Fan on April 12, 2014, 09:39:54 pm

author: Dago
author_rank: Frequent Contributor
timestamp: April 21, 2014, 07:04:03 am
content: Quote from: Electro Fan on April 21, 2014, 01:28:51 amThe frequency counter is "counting edges" and baud is not the same thing as frequency. If the symbol has a lot of zeros then the frequency will be lower because there is less edges... makes sense?

author: David_AVD
author_rank: Super Contributor
timestamp: April 21, 2014, 07:24:15 am
content: Quote from: Dago on April 21, 2014, 07:04:03 amWell, lots of adjacent ones and zeros anyway. All ones and all zeros will have the fewest edges.

author: Electro Fan
author_rank: Super Contributor
timestamp: April 21, 2014, 11:23:16 pm
content: Quote from: SL4P on April 21, 2014, 04:14:09 amHi SL4P,Thanks for reminding us of all that - without a doubt those are still objectives within the overall goal. Given the feedback here I'm working on all the "easy"parts first but I'd like to get back to - or move on to - a solution that would give fuller control of the various waveform attributes. I'm open to any suggestions on how to do it all including gaining control over the amplitude and pulse durations and the underlying clock frequency (especially on a bit by bit basis in addition to a byte by byte basis).Seems to me there should be some beginner's curriculum somewhere that covers Ohm's Law, Power Supplies, the ability to create and manage waveform voltage (amplitude), frequency, pulse durations, etc. using an oscilloscope in a way that teaches A-D, decoding, etc. - maybe with Arduino hardware and software, etc. - something that would help beginners put a few key concepts together. I'm sure there is a class out there but in the meantime it gives us all something to discuss which gives us a combination of this, that, and the next thing, and sometimes this, and hopefully this overall:EF

author: Electro Fan
author_rank: Super Contributor
timestamp: April 21, 2014, 11:47:23 pm
content: Quote from: Dago on April 21, 2014, 07:04:03 amI knowOk, I get that edge counts will vary depending on the particular character combinations (and the associated transitions) of 1s and 0s - and therefore any frequency counter or measurement based on edge counts will vary. No problem.But just to clarify, the display in the upper right hand corner is what I'm referring to as "the counter" (I think that's what Rigol calls it). Is this display in the upper right hand corner showing the frequency of edge counts (or something else)?Along the bottom of the scope display is another measurement (which is where various measurements can be selected and placed) showing "frequency" - what is this display showing (what frequency is it measuring), and why does it vary so much?Seems to me that given the frequency variation on the bottom measurement that it is more likely to be showing frequency based on edge counts (since it varies so much), and the counter at the top is more likely to measure the clock frequency since it seems to be much more stable - but hey, that's why this is the Beginner Forum.Thanks, EF

author: SL4P
author_rank: Super Contributor
timestamp: April 22, 2014, 01:01:52 am
content: ElectroFan - where do you live?I'm in forced semi-retirement (health), and haveplentyof time to explore this over coffee.Cheers