Arduino Curiosity

Question for the programming experts.

I have five Arduino UNOs all programmed as a random lighting controller with the same sketch. All five Arduinos start with port #9 active, every time. My curiosity is why #9 every time. I don’t have a problem with it being #9, just curious.

This is my Sketch:

#define numleds 14
byte ledpins = { 0,1,2,3,4,5,6,7,8,9,10,11,12,13 } ;
void setup( ) { &nbs

That’s because the random() function is not random, it’s psuedorandom. If you watch carefully, you should be seeing the exact same sequence every time you run the program. There is also the randomseed() function which generates a new seed number for the random() function. This is from the Arduino site:

If it is important for a sequence of values generated by random() to differ, on subsequent executions of a sketch, use randomSeed() to initialize the random number generator with a fairly random input, such as analogRead() on an unconnected pin.

–Randy

Mel,

One thing I’ve noticed is that your setup routine is a little off. You’ve got the LED pins defined as 0-13, but the for loop goes from 1-14 (i = 1, numleds = 14). As such, when you run it, pin 0 will be undefined, and pin 14 will be set up as an output even though it’s not in use.

As for why pin #9, I suspect it’s because the Arduino random function is really pseudo-random. Namely, it returns the next member in a sequence of numbers, and this sequence is actually set, not generated. As such, it’ll return the same numbers for each execution. It would appear that the output of the random function is triggering the conditions to activate pin 9 each time the sketch is run.

The randomseed function (https://www.arduino.cc/en/Reference/RandomSeed) initiates the random number generator to a different point in the sequence. I would suggest putting this in your startup routine, to initiate the random number generator. There are two approaches you could take:

  1. Put a different number in the randomseed function for each Arduino.

  2. Perform an analogread() on an undefined & unused analog pin, and feed this into the randomseed function on startup. Given that the analog pin isn’t in use, the value of the read from it will be random.

I’ve used approach no. 2 in my own programming.

Thanks for your input guys!

I’m not a programmer! I’m an old electronics guy, a very old electronics guy!

All 14 ports in my sketch work as is. I didn’t notice that all the Arduinos had the same sequence, I seldom turn them on at the same time so I guess that puts them out of sync and not noticeable.

I don’t believe in fixing something that isn’t broke so I don’t think I’ll attempt to change my sketch. It took some doings just to get it to work and I’m afraid if I attempt to change it I’ll screw it up.

Edit:

This is the light placement in my current build, all lights work.

“sketch?”

Why not, oh, say… “program?”

As others have noted, your “for” loop doesn’t include port 0. The Arduino pins default to inputs, and writing “high” to an input enables its internal resistor, which will dim your LED, though as you have observed it still works.

I get that if you don’t want to change your code that’s fine, but it just takes a few seconds, so I’ve copied your code here with the appropriate changes others have already mentioned in case you change your mind:

Speedy
I gave your Sketch a shot and I like the operation better than mine. It seems that the change screwed up the timing. I changed the delay to 8 seconds and that seems to work better.

More later, I’m dinking with the sketch.

Mel

Modeling the early to mid 1950s SP in HO scale since 1951

My Model Railroad
http://melvineperry.blogspot.com/

Bakersfield, California

I’m beginning to realize that aging is not for wimps.

Randy and Danny after I made the changes you suggested I couldn’t get it to compile. That’s pretty much normal for me.

Speedy, the 8 second delay looks pretty good.

There is one change, now it starts every time at 14, that’s understandable.

Mel

Modeling the early to mid 1950s SP in HO scale since 1951

My Model Railroad
http://melvineperry.blogspot.com/

Bakersfield, California

I figured that Arduino uses “sketch” for “program.”

It annoys me. It annoys me when neologims are used for concepts we already have words for. It’s one of the things that pissed me off so much about Java. Enough with the “cute” coffee puns already, those things all have names.

Arduino was originally designed for artists. The word ‘program’ scares artists. So they called it a ‘sketch’. I am not an artist (the mess in front of me as I try to draw out even a simple schematic for a Tortoise controlling signals in a good example - but none of the electronic CAD programs I have contain a Tortoise as a component. LEDs, sure. Diodes, Sure. Turtles? Nope). I write programs for my Arduinos - actually I only use the Arduinos for development, my finished project will have just the ATMegas 328P microcontroller and supporting components. In fact, half the time I use Visual Studio to develop my programs rather than the Arduino IDE.

–Randy

I’ve dinked around with the timing for three hours and while I like some of the changes there are some that I don’t like. I placed the new house on my layout close to a house with my original sketch and the RandomSeed change looks strange compared to just Random but maybe that’s good.

At this point I’m using 5 seconds for delay and (5,150) >60) for the if statement with RandomSeed.

A plus for the RandomSeed is the bulbs randomly stay on longer. Before the change the average current draw (bulb on time) was 200ma, after the change the average current is 400ma+. All lights on max draw is 550ma.

This is what I ended up with:

#define numleds 14

The sketch/programming language used in the Arduino is a version of the ‘c’ programming language. If interested, obtain a book on the Arduino ‘c’ as that ‘c’ is not a full ‘c’ or ‘c++’. Confusing![:O]

can you give an example of something you can do in c/c++ that you can’t do on an Arduino?

Well, Arduino isn’t directly based on C or C++, it’s actually based on Wiring. It’s very close to C++ but not exactly the same. Unless you’re a hardcore C++ programmer, it doesn’t really matter much.

You can of course directly access the micro’s control registers in Arduino, or program an Arduino using Atmel Studio and use ‘pure’ C. To do so, you directly manipulate the control registers and port registers in the Atmega chip. It’s WAY faster than pinMode, digitalWrite, and digitalRead. But you need to keep track of each bit of the port register yourself and use bitmasking to turn a given pin on and off. If you need ultimate performance, direct control in Arduino is the first step. If that’s STILL not fast enough, then direct programming with Atmel Studio is the way to go. They may only be 8 bit, and run at 16MHz, but the ATMega 328 used in the Uno and Nano are actually pretty fast. Most of the things we need for model railroads, the speed you get using the Arduino IDE to code is plenty fast enough.

–Randy

i see gcc tools under ther hardware/. Looks like it’s using the GNU compiler which is standard c/c++ which we use on our small-cell project.

don’t understand how accessing HW registers is relavent to the question.

There are various ways of accessing HW registers affecting multiple I/O pins with different features and performance. This is an age old problem. Can’t you write your own version versions of digitalWrite/Read that are faster, if needed?

still looking for an example

You should be able to use an C/C++ construct, so long as you observe the limits of the microcontroller - there are differences around floating point support since the ATMega series used in common Arduinos is only an 8 bit processor and doesn’t have the scratch register space to to high precision math. This affects double and float types - it’s pretty well documented on the Arduino site.

The reverse is not true though, since Arduino’s flavor has extensions from Wiring as part of the language which will not be in standard C/C++. This is where the HW register access is relevent. Unless you write your own routines and call them the same name, an Arduino program won’t compile in stock C.

Does any of it matter? You can program these things with anything you are comfortable with. The Arduino IDE is a bit simplistic and doesn’t do much more than I can do with Notepad++ but you can always use the Visual Studio add-in that I do and leverage VS (free edition even) as a superior IDE yet still have the convenience of a button to upload the program to the Arduino like in the Arduino IDE. Or you can go whole hog and use Atmel Studio (which is VS with Atmel’s add ins) and write directly to the hardware. There’s a lot of animosity on the aprt of ‘professional’ embedded programmers towards the Arduino IDE. True it is lacking compared to high end professional development systems, but it does get the job done and allows people who might not be able to do so to write working code. I think it’s a good thing, as it hides the complexity of working with the HW registers and lets you focus on just learning the C syntax and program flow. Once you’ve got that down you can take the next step and replace all the digitalWrite, digitalRead, and pinMode stuff with direct register access. One step at a time.

–Randy

Arduino Wiring Guide as used at a college.

are you guys suggesting that Arduino C is not standard C because functions like pinmode() and DigitalWrite() aren’t part of any standard C library?

There are some differences in data types as well. boolean and byte aren’t standard C types. They do map to bool and unsigned char for the most part but Arduino code with such type declarations won;t just compile in a C compiler.

It’s close enough, but it’s not exactly standard C.

–Randy

i’m curious how people understand what a language is.

one difference I see is that the IDE must wrap the .ino file within another more standard c/cpp file with additional includes (one reason it’s not a .c/cpp file). One include is Arduino.h (hardware/arduino/avr/cores/arduino/Arduino.h). I need to explicitly include arduino.h in my .c/cpp files in multi-file projects.

Arduino.h includes several standard includes (e.g. stdlib, string, math), common Arduino #defines (e.g. HIGH, INPUT_PULLUP), typedefs (e.g. boolean, byte), and function declarations (e.g. pinMode, analogWrite, delay).

these things (e.g. HIGH, byte, delay()) are not part of the language, they are conventional customizations for the Arduino environment.

arduino.h uses typedefs to define new data types from existing ones:

typedef unsigned int word;
typedef bool boolean;
typedef uint8_t byte;

bool is a standard C++ data type and uint8_t is typedef’d in stdint.h as unsigned char. Unsigned int is standard C which doesn’t define the size of an int.

I have taken Arduino code, added these typedefs and stubs for pinMode(), digitalWrite(), …, and compiled an Arduino application with the standard GNU compiler (I use cygwin on windows). This is a good way to simulate and save time during embedded program development.

Our small-cell project is required to use stdint.h which defines uint8_t, int16_, uint32_t, … for variabl