Professional Documents
Culture Documents
Reference Jump
Starter
Written for RenBED
By Jon Fuge
Jon.fuge@renishaw.com
December 3 2013
/*******************************************************************************
* This program counts forever *
Title block makes it easy to
* *
see what’s happening.
* Jon Fuge *
* V1.0 25/11/2013 First issue of code *
*******************************************************************************/
#include "mbed.h" // include “mbed.h” The initial of the type has
been added in lowercase
/* Declare global variables and constants before main() */
before the names of
const char cINCREMENT = 1; // Increment step size variables and constants.
int main () // This is the “main” function to run. The names of constants
{
// local variables declared in a function. are in CAPITALS.
char cMyCounter = 0; // Counter variable
The names of variables
for (;;) // This starts the infinite loop
{ are in CamelText.
cMyCounter = cMyCounter + cINCREMENT;
} // end of for (;;)
} // end of main () Comments have been Extra lines have been
added to the end of added to make the
Indents are used to code blocks to make code readable
make the code clear. them easy to identify.
The compiler does its own job of adding colour to the text.
Comments are green!
o Single line comments start with “//” no end needs to be defined, a new line will do that for you.
o Multiline comments start with “/*” and have to end with “*/”
Keywords (special built in reserved words) are blue!
Compiler directives (tell the compiler how to compile the code) and numbers are shown in red!
Strings (special arrays of characters used as text) are pink.
Everything else is black.
The program example includes a constant and a variable, but for either to be useful, we need to be able to “operate”
with them. For that purpose, C++ integrates operators. Unlike other languages whose operators are mainly
keywords, operators in C++ are mostly made of signs that are not part of the alphabet but are available in all
keyboards. This makes C++ code shorter and more international, since it relies less on English words.
You cannot use keywords for variable, constant, function or procedure names.
Enumeration
Enumeration is a little bit like assigning sequential numbers to a series of constants. If we wanted to assign constants to the
days of the week like SUN = 0, MON = 1, TUE = 2, etc… we could write the following code:
enum DaysOfTheWeek { SUN , MON, TUE, WED, THUR, FRI, SAT };
We don’t have to start at 0, but can specify any start we want: Tip… Use \ if your code
needs to go over multiple
enum MonthsOfTheYear { JAN = 1, FEB, MAR, APR, MAY, JUN,\ lines.
JUL, AUG, SEP, OCT, NOV, DEC};
It used to be important to consider what technology of microcontroller you are using. Older microcontrollers were
generally 8-bit, and could handle 8-bit numbers very well, but had to use 4 times the effort for 16-bit numbers and 8
times the effort to handle 32-bit numbers, dependent on which type of processor. We have no concerns with RenBED
because it uses a powerful 32-bit ARM processor so it can handle 32-bit numbers as effortlessly as 8-bit numbers.
Constants are used to store a number that will never change, one such number could be a value for PI (π), or it could
be a control parameter such as, MAXIMUM_SPEED = 155. Constants are used to avoid “magic numbers” which are
numbers placed with no explanation. Variables store numbers, which are modified by the program; these are
particularly useful allowing your program to count and process information.
Arrays can be constants or variables. An array is a group of same type data grouped sequentially and accessible by an
index. Arrays start at 0, so char cDiameter[4] contains cDiameter[0], cDiameter[1], cDiameter[2], cDiameter[3].
cMatrix[0][1]:
cMatrix[0][2]:
cMatrix[1][0]:
cMatrix[1][1]:
cMatrix[1][2]:
sNumberOfPens:
cClassSize:
char cClassSize = 15;
char cMatrix[2][3] = {{2,3,5},{7,11,13}};
short sNumberOfPens = 2000;
15 2 3 4 5 11 13 208 7
sNumberOfPens gets split into two 8 bit numbers (lowest 8 bits first). If we convert 2000 into Hexadecimal, we get
0x07D0. This gets stored as 0xD0 (208 decimal) in the first location and 0x07 (7 decimal) in the second.
By default all variables are auto, auto means that the variable will only exist during the life of a function or procedure,
once the function has completed, the variable is lost. Although auto is a keyword, it is rarely used. static is the
opposite of auto, static defines a variable as being persistent so its value is preserved once the function or procedure
has exited; upon re-entry to the function, the previous variable value remains as it was.
register lets you store a variable in a processor register (hardware rather than memory). This is declared in a similar
way to other variables but is rarely used because the compiler automatically chooses the best optimisation for storage.
volatile is the extreme opposite of const and indicates that a variable can be changed unpredictably despite
observing the normal program flow. Examples could be timer registers, interrupt handler storage etc.
The function sizeof returns the number of bytes used by a variable or array. sizeof is useful for determining the size
of a buffer to ensure that you have not exceeded the storage capacity.
Enumeration example
/*******************************************************************************
* This program demonstrates the use of enumeration *
* *
* Jon Fuge *
* V1.0 26/11/2013 First issue of code *
*******************************************************************************/
#include "mbed.h" Tip… Use \ if your code
#include "USBSerial.h"
needs to go over multiple
enum DaysOfTheWeek { SUN , MON, TUE, WED, THUR, FRI, SAT }; lines.
enum MonthsOfTheYear { JAN = 1, FEB, MAR, APR, MAY, JUN,\
JUL, AUG, SEP, OCT, NOV, DEC};
USBSerial serial; // Virtual serial port over USB. Use Teraterm as the interface
int main() {
wait (10); // Wait 10 seconds to connect port
serial.printf("Sunday is day %i, April is the %i month of the year\n\r", SUN, APR);
for(;;) {} // Loop forever
} Output is:
Sunday is day 0, April is the 4 month of the year
Assignment operator:
Number Operation Example
= Assign value on right to part on the left char cMyCounter = 0; // Counter variable
/*******************************************************************************
* This program demonstrates decimal, octal and hexadecimal *
* *
* Jon Fuge *
* V1.0 01/12/2013 First issue of code *
*******************************************************************************/
#include "mbed.h"
#include "USBSerial.h"
//Virtual serial port over USB. Use Teraterm or other terminal as the interface
USBSerial serial;
int main() {
const char cRVALUE1 = 0x86; // 10000110 in binary!
char clvalue; // Store our result here!
wait (5); // Wait 5 seconds to connect port
clvalue = cRVALUE1; Output is:
serial.printf("%X = %X\n\r", cRVALUE1, clvalue); 86 = 86
for(;;) {} // Loop forever
}
Relational Operators
Relational operators allow you to compare two values. The comparison is done with an lvalue and an rvalue, the
operator defines what comparison is to be performed; the result of the comparison is given as a Boolean value (either
TRUE or FALSE). Relational operators are often used with if, while, for etc.
/*******************************************************************************
* This program demonstrates decimal, octal and hexadecimal *
* Jon Fuge * Output is:
* V1.0 01/12/2013 First issue of code * cValue == 43
*******************************************************************************/ cValue != 50
cValue > 42
#include "mbed.h" cValue > 44
#include "USBSerial.h" cValue >= 32
cValue >= 54
//Virtual serial port over USB. Use Teraterm or other terminal as the interface
USBSerial serial;
int main() {
char cValue = 43; // Create 3 values
Relational operators:
wait (5); // Wait 5 seconds to connect port Operator Operation
if (cValue == 43) serial.printf("cValue == 43\n\r"); == Equal to
if (cValue != 50) serial.printf("cValue != 50\n\r"); != Not Equal to
if (cValue > 42) serial.printf("cValue > 42\n\r"); > Greater than
if (cValue < 44) serial.printf("cValue > 44\n\r");
if (cValue >= 32) serial.printf("cValue >= 32\n\r");
< Less than
if (cValue <= 54) serial.printf("cValue >= 54\n\r"); >= Greater than or equal to
while(cValue == 43) {} // Loop forever <= Less than or equal to
}
/*******************************************************************************
* This program demonstrates decimal, octal and hexadecimal *
* Jon Fuge *
* V1.0 01/12/2013 First issue of code *
*******************************************************************************/
#include "mbed.h"
#include "USBSerial.h" Logical operators:
Operator Operation
//Virtual serial port over USB.
USBSerial serial;
&& Logical AND
|| Logical OR
int main() { ! Logical NEGATION
char cValue = 43; // Create 3 values
wait (5); // Wait 5 seconds to connect port
if ((cValue < 50) || (cValue > 100)) serial.printf("cValue is under 50 or over 100\n\r");
if ((cValue > 40) && (cValue < 50)) serial.printf("cValue is between 40 and 50\n\r");
if ((cValue < 50) && !(cValue == 40)) serial.printf("cValue is less than 50 and not 40\n\r");
while(cValue == 43) {} // Loop forever
} Output is:
cValue is under 50 or over 100
cValue is between 40 and 50
cValue is less than 50 and not 40
/*******************************************************************************
* This program demonstrates decimal, octal and hexadecimal *
* *
* Jon Fuge *
* V1.0 01/12/2013 First issue of code *
*******************************************************************************/
#include "mbed.h"
#include "USBSerial.h"
//Virtual serial port over USB. Use Teraterm or other terminal as the interface
USBSerial serial;
int main() {
Number representations:
char cDecimal = 20; // This is 20 in decimal! Number Representation
char cOctal = 020; // This is 16 in decimal! 20 By default, all numbers are decimal “20”
char cHexadecimal = 0x20; // This is 32 in decimal! 020 Lead “0” is octal, decimal “16”
0x20 Lead “0x” is hexadecimal, decimal “32”
wait (5); // Wait 5 seconds to connect port
serial.printf("Display values as decimal:\n\r");
serial.printf("cDecimal = %i, cOctal = %i, cHexadecimal =%i\n\r", cDecimal, cOctal, cHexadecimal);
serial.printf("Display values as octal:\n\r");
serial.printf("cDecimal = %o, cOctal = %o, cHexadecimal =%o\n\r", cDecimal, cOctal, cHexadecimal);
serial.printf("Display values as hexadecimal:\n\r");
serial.printf("cDecimal = %X, cOctal = %X, cHexadecimal =%X\n\r", cDecimal, cOctal, cHexadecimal);
for(;;) {} // Loop forever
} Output is:
Display values as decimal:
cDecimal = 20, cOctal = 16, cHexadecimal =32
Display values as octal:
cDecimal = 24, cOctal = 20, cHexadecimal =40
Display values as hexadecimal:
cDecimal = 14, cOctal = 10, cHexadecimal =20
/*******************************************************************************
* This program demonstrates various arithmetic operators *
* Jon Fuge *
* V1.0 02/12/2013 First issue of code *
*******************************************************************************/
#include "mbed.h" Output is:
#include "USBSerial.h" 43 + 7 = 50
43 ‐ 7 = 36
//Virtual serial port over USB. Use Teraterm or other terminal as the interface 43 * 7 = 301
USBSerial serial; 43 / 7 = 6
43 % 7 = 1
int main() {
char crvalue1 = 43; // random decimal iRValue = 43
char crvalue2 = 7; // random decimal iLValue = iRValue++
int clvalue; // Store our result here! iLValue = 43, iRValue = 44
wait (5); // Wait 5 seconds to connect port iRValue = 43
clvalue = crvalue1 + crvalue2; iLValue = ++iRValue
serial.printf("%i + %i = %i\n\r", crvalue1, crvalue2, clvalue); iLValue = 44, iRValue = 44
clvalue = crvalue1 ‐ crvalue2;
serial.printf("%i ‐ %i = %i\n\r", crvalue1, crvalue2, clvalue); iRValue = 43
clvalue = crvalue1 * crvalue2; iLValue = iRValue‐‐
serial.printf("%i * %i = %i\n\r", crvalue1, crvalue2, clvalue); iLValue = 43, iRValue = 42
clvalue = crvalue1 / crvalue2;
serial.printf("%i / %i = %i\n\r", crvalue1, crvalue2, clvalue); iRValue = 43
clvalue = crvalue1 % crvalue2; iLValue = ‐‐iRValue
serial.printf("%i %% %i = %i\n\r\n\r", crvalue1, crvalue2, clvalue); iLValue = 42, iRValue = 42
serial.printf(" iRValue = %i\n\r", crvalue1);
clvalue = crvalue1++;
serial.printf("iLValue = iRValue++\n\riLValue = %i, iRValue = %i\n\r\n\r", clvalue, crvalue1);
crvalue1 = 43; // reset crvalue1
serial.printf(" iRValue = %i\n\r", crvalue1);
clvalue = ++crvalue1;
serial.printf("iLValue = ++iRValue\n\riLValue = %i, iRValue = %i\n\r\n\r", clvalue, crvalue1);
crvalue1 = 43; // reset crvalue1
serial.printf(" iRValue = %i\n\r", crvalue1);
clvalue = crvalue1‐‐;
serial.printf("iLValue = iRValue‐‐\n\riLValue = %i, iRValue = %i\n\r\n\r", clvalue, crvalue1);
crvalue1 = 43; // reset crvalue1
serial.printf(" iRValue = %i\n\r", crvalue1);
clvalue = ‐‐crvalue1;
serial.printf("iLValue = ‐‐iRValue\n\riLValue = %i, iRValue = %i\n\r\n\r", clvalue, crvalue1);
for(;;) {} // Loop forever
}
Bitwise operators:
Operator Operation Example function Result
& AND returns 1 if both bits are 1 10000110 & 00010011 = 00000010
| OR returns 1 if either or both bits are 1 10000110 | 00010011 = 10010111
^ XOR returns 1 if bits are complementary 10000110 ^ 00010011 = 10010101
~ Complement (invert) each bit ~10000110 = 01111001
<< Shift left by (rvalue) bits 10000110 << 0x02 = 00011000
>> Shift right by (rvalue) bits 10000110 >> 0x02 = 00100001
/*******************************************************************************
* This program demonstrates various bitwise operators *
* *
* Jon Fuge *
* V1.0 01/12/2013 First issue of code *
*******************************************************************************/
#include "mbed.h"
#include "USBSerial.h"
//Virtual serial port over USB. Use Teraterm or other terminal as the interface
USBSerial serial;
int main() {
char crvalue1 = 0x86; // 10000110 in binary!
char crvalue2 = 0x13; // 00010011 in binary!
char crvalue3 = 0x02; // 00000010 in binary!
char clvalue; // Store our result here!
wait (5); // Wait 5 seconds to connect port
clvalue = crvalue1 & crvalue2;
serial.printf("%X & %X = %X\n\r", crvalue1, crvalue2, clvalue);
clvalue = crvalue1 | crvalue2;
serial.printf("%X | %X = %X\n\r", crvalue1, crvalue2, clvalue);
clvalue = crvalue1 ^ crvalue2;
serial.printf("%X ^ %X = %X\n\r", crvalue1, crvalue2, clvalue);
clvalue = ~crvalue1;
serial.printf("~%X = %X\n\r", crvalue1, clvalue);
clvalue = crvalue1 << crvalue3;
serial.printf("%X << %X = %X\n\r", crvalue1, crvalue3, clvalue);
clvalue = crvalue1 >> crvalue3;
serial.printf("%X >> %X = %X\n\r", crvalue1, crvalue3, clvalue);
serial.printf("\n\r"); // add another blank line Output is:
for(;;) {} // Loop forever 86 & 13 = 2
} 86 | 13 = 97
86 ^ 13 = 95
~86 = 79
The program above repeats the calculation examples. 86 << 2 = 18
86 >> 2 = 21
The example below toggles a LED on and off when a switch is pressed, the switch is connected between DIP5 (P0_9)
& 0V, and the LED with resistor is connected between DIP36 (P0_21) and 0V.
/*******************************************************************************
* This program demonstrates how to read a switch and toggle a LED. *
* Connect LED and resistor between to DIP36 (P0_21) and DIP1 (0V). *
* Connect switch between DIP5 (P0_9) and DIP1 (0V). *
* *
* Jon Fuge *
* V1.0 12/11/2013 First issue of code *
*******************************************************************************/
#include "mbed.h" // has prototypes for DigitalIn and DigitalOut
DigitalIn mybutton(P0_9); // mybutton reads bit 9 of port 0 (DIP5).
DigitalOut myled(P0_21); // myled controls bit 21 of port 0 (DIP36).
int main() {
mybutton.mode(PullUp); // Configure pin to be a pull‐up input
for(;;) { //Create infinite loop to keep program running.
if (mybutton == 0) { // if mybutton = 0, then it has been pressed
myled = !myled; // myled will now become !myled (! means NOT).
wait(0.1); // Wait for 0.1 seconds to "debounce" the switch.
while (mybutton == 0) {} // Wait for my button to be released.
} // End of if (mybutton == 0)
} // End of for(;;)
} // end of int main()
DigitalIn PinName(PortName);
Creates a DigitalIn called PinName, which is connected to the specified PortName.
DigitalIn mybutton(P0_9); // mybutton reads bit 9 of port 0 (DIP5).
PinName.mode(PinMode);
Allows you to specify what type of input your digital input is.
After a reset, pins P0_4 & P0_5 are configured as OpenDrain, all other pins are configured as PullUp.
mybutton.mode(PullUp); // Configure pin to be a pull‐up input
Pin modes:
Mode Operation
PullUp When PullUp is selected, a current of 50µA is applied to the pin pulling it high.
PullDown When PullDown is selected, a current of 50µA is applied to the pin pulling it low.
PullNone When PullNone is selected, the input is left floating so you will need to pull it high or low.
When PullNone is selected, the input can get a bit smelly , no actually it is like the floating input
OpenDrain
before, but also has the ability to pull itself low so it can be used as a input/output.
PinName
When PinName is used on its own, it operates as a function which returns the digital level of the input pin as a 0 (Low),
or a 1 (High).
if (mybutton == 0) { // if mybutton = 0, then it has been pressed
DigitalOut PinName(PortName);
Creates a DigitalOut called PinName, which is connected to the specified PortName.
DigitalOut myled(P0_21); // myled controls bit 21 of port 0 (DIP36).
PinName
When PinName is used on its own, it is used to set the output state of the pin, PinName can also be used as a function in the
same way as DigitalIn which returns the level of the output as a 0 (Low), or a 1 (High).
myled = !myled; // myled will now become !myled (! means NOT).
A separate multiplexor (MUX) wire selects which display to drive, when set to 0, D5 (left) is driven, when set to 1, D6
(right) is driven.
/*******************************************************************************
* This program demonstrates how to drive the seven segment display *
* *
* Jon Fuge *
* V1.0 13/12/2013 First issue of code *
*******************************************************************************/
#include "mbed.h"
#include "SevenSegLed.h"
// Lets define some "macros" to make the code easier to read
#define mUnits D_7seg[1] // "mUnits" will be substiuted for "D_7seg[1]"
#define mTens D_7seg[0] // "mTens" will be substiuted for "D_7seg[0]"
#define mDot D_dot[1] // "mDot" will be substiuted for "D_dot[1]"
void attimeout(); //declare prototype for timeout handler.
//configure sevensegled pin connection mapping.
//
// common type (0:anode common 1:cathode common)
// | display mode (0:smooth 1:hard)
// | | segA segB segC segD segE segF segG segP com1 com2
SevenSegLed segmentled(0, 0, P1_23, P1_28, P0_16, P1_31, P1_13, P1_16, P1_19, P0_23, p21, P1_25);
//Define two arrays to house the data to be outputted. D_7seg can contain digits 0‐F and D_dot 0‐1.
//
// 0 1 //0 = leftmost digit, 1 = rightmost digit
// | |
uint8_t D_7seg[2] = {0, 0}; // number (0x00:"0", ... , 0x09:"9", 0x0A:"A", ... , 0x0F:"F", other:" ")
uint8_t D_dot[2] = {0, 0}; // dotpoint. (0:off 1:on)
Ticker timeout; //Create an instance of class Ticker called timeout.
int main()
{
timeout.attach_us(&attimeout, 500000); // Set up interrupt to call attimeout() every half a second.
for(;;) {
segmentled.SevenSegLed_main(D_7seg, D_dot); // Keep the displays multiplexed.
}
}
void attimeout() //Timer interrupt routine.
{
mDot = 1 ‐ mDot;
if (mDot == 1) {
mUnits++; // This means the same as D_7seg[0] = D_7seg[0] + 1; Increment "units"
if (mUnits > 9) { // "units" digit should be in the range 0 ‐> 9
mUnits = 0; // Reset the "units" to 0
mTens++; // Increment "tens" digit
if (mTens > 9) { // "tens" digit should be in the range 0 ‐> 9
mTens = 0; // Reset the "tens" to 0
}
}
}
}
Printf parameters:
Parameters start with % and are arranged in the following way..
%[flags][width][.precision][length]specifier
Items held in [ ] are optional, but the specifier must always exist.
The format specifier can also contain sub-specifiers: flags, width, .precision and modifiers (in that order), which are
optional and follow these specifications:
flags:
Flags Description
‐ Left-justify within the given field width; Right justification is the default (see width sub-specifier).
Forces to precede the result with a plus or minus sign (+ or -) even for positive numbers. By default, only
+
negative numbers are preceded with a - sign.
(space) If no sign is going to be written, a blank space is inserted before the value.
Used with o, x or X specifiers the value is preceded with 0, 0x or 0X respectively for values different than
zero.
#
Used with a, A, e, E, f, F, g or G it forces the written output to contain a decimal point even if no more
digits follow. By default, if no digits follow, no decimal point is written.
Left-pads the number with zeroes (0) instead of spaces when padding is specified (see width sub-
0
specifier).
width:
Width Description
Minimum number of characters to be printed. If the value to be printed is shorter than this number, the
(number)
result is padded with blank spaces. The value is not truncated even if the result is larger.
The width is not specified in the format string, but as an additional integer value argument preceding
*
the argument that has to be formatted.
length:
The length sub-specifier modifies the length of the data type. This is a chart showing the types used to interpret the
corresponding arguments with and without length specifier (if a different type is used, the proper type promotion or
conversion is performed, if allowed):
Specifiers
Flags
di uoxX feEgG c s
(none) int unsigned int double int char*
hh signed char unsigned char
h short int unsigned short int
l long int unsigned long int int char*
ll long long int unsigned long long int
j intmax_t uintmax_t
z size_t size_t
t ptrdiff_t ptrdiff_t
L long double
In addition to printf parameters, printf also allows you to enter ASCII control characters. In order to inform printf that
you want to use a control character you start an “escape sequence” with a ‘\’” slash character. The table below lists the
escape sequences available.
Specifier ASCII (American Standard Code for Information Interchange) ASCII Name
\a Audible alert (bell) BEL
\b Backspace BS
\t Horizontal tab HT
\n Newline LF
\v Vertical tab VT
\f Formfeed FF
\r Carriage return CR
\” Double quote “
\’ Single quote ‘
\? Question mark ?
\\ Backslash /
/*******************************************************************************
* This program demonstrates the use of printf escape sequences *
* *
* Jon Fuge *
* V1.0 19/12/2013 First issue of code *
*******************************************************************************/
#include "mbed.h"
#include "USBSerial.h"
//Virtual serial port over USB. Use Teraterm or other terminal as the interface
USBSerial serial;
int main()
{ Output is:
wait (5); audible alert (bell) || \a 7
serial.printf ("audible alert (bell) |\a| \\a %d\n\r" , '\a'); backspace | \b 8
serial.printf ("backspace |\b| \\b %d\n\r" , '\b'); horizontal tab | | \t 9
serial.printf ("horizontal tab |\t| \\t %d\n\r" , '\t'); newline |
serial.printf ("newline |\n| \\n %d\n\r" , '\n'); | \n 10
serial.printf ("vertical tab |\n| \\v %d\n\r" , '\v'); vertical tab |
serial.printf ("formfeed |\f| \\f %d\n\r" , '\f'); | \v 11
serial.printf ("carriage return |\r| \\r %d\n\r" , '\r'); formfeed |
serial.printf ("double quote |\"| \\\" %d\n\r", '\"'); | \f 12
serial.printf ("single quote |\'| \\\' %d\n\r", '\''); | \r 13eturn |
serial.printf ("question mark |\?| \\? %d\n\r" , '\?'); double quote |"| \" 34
serial.printf ("backslash |\\| \\\\ %d\n\r", '\\'); single quote |'| \' 39
for (;;) {}; question mark |?| \? 63
} backslash |\| \\ 92
/*******************************************************************************
* This program demonstrates the use of printf parameters *
* *
* Jon Fuge *
* V1.0 16/12/2013 First issue of code *
*******************************************************************************/
#include "mbed.h" Output is:
#include "USBSerial.h" Characters: a A
Decimals: 1977 650000
//Virtual serial port over USB. Preceding with blanks: 1977
USBSerial serial; Preceding with zeros: 0000001977
Some different radices: 100 64 144 0x64 0144
int main() floats: 3.14 +3e+00 3.141600E+00
{ Width trick: 10
wait (5); A string= 21
serial.printf ("Characters: %c %c \n\r", 'a', 65);
serial.printf ("Decimals: %d %ld\n\r", 1977, 650000L);
serial.printf ("Preceding with blanks: %10d \n\r", 1977);
serial.printf ("Preceding with zeros: %010d \n\r", 1977);
serial.printf ("Some different radices: %d %x %o %#x %#o \n\r", 100, 100, 100, 100, 100);
serial.printf ("floats: %4.2f %+.0e %E \n\r", 3.1416, 3.1416, 3.1416);
serial.printf ("Width trick: %*d \n\r", 5, 10);
serial.printf ("%s \n\r", "A string");
for (;;) {};
}
%[*][width][length]specifier
Items held in [ ] are optional, but the specifier must always exist.
The format specifier can also contain sub-specifiers: flag, width and length (in that order), which are optional and follow
these specifications:
flags:
Flags Description
An optional starting asterisk indicates that the data is to be read from the stream but ignored (i.e. it is not
*
stored in the location pointed by an argument).
width Specifies the maximum number of characters to be read in the current reading operation (optional).
One of hh, h, l, ll, j, z, t, L (optional).
length
This alters the expected type of the storage pointed by the corresponding argument (see below).
length:
The length sub-specifier modifies the length of the data type. This is a chart showing the types used to interpret the
corresponding arguments with and without length specifier (if a different type is used, the proper type promotion or
conversion is performed, if allowed):
Specifiers
Flags
di uoxX feEgG c s
(none) int unsigned int double int char*
hh signed char unsigned char
h short int unsigned short int
l long int unsigned long int int char*
ll long long int unsigned long long int
j intmax_t uintmax_t
z size_t size_t
t ptrdiff_t ptrdiff_t
L long double
The next few pages of this booklet will deal with how to use each of the USB device classes and provide examples of
their use.
The example below shows a very simple way to communicate with the USB virtual serial port using printf to send a
message to the port, and scanf to receive a message from the port.
/*******************************************************************************
* This program demonstrates how to read a string from the USB serial device *
* and write a string back to the USB serial device *
* *
* Jon Fuge *
* V1.0 25/11/2013 First issue of code *
*******************************************************************************/
#include "mbed.h"
#include "USBSerial.h"
//Virtual serial port over USB. Use Teraterm or other terminal as the interface
USBSerial serial;
int main() {
char buf[128]; // A char array is also a string!
wait (10); // Wait 10 seconds to connect port
// Need to type a key, then enter to get a response.
serial.printf("What is your name?\n\r"); // Send message to USB serial port
serial.scanf("%s", buf); // Receive message from USB serial port
serial.printf("What are you doing %s?\n\r", buf);
for(;;) {} // Loop forever Output is:
} What is your name?
Jon
What are you doing Jon?
When RenBED has connected to your computer using the USBSerial protocol for the first time, windows will try to find
an existing driver without success. Follow the instructions mentioned below to install the driver:
http://mbed.org/handbook/USBSerial
You will require a “terminal emulator” to provide you with a window, in addition to the USB serial driver, which can
communicate with a serial port device. For older computers Windows includes a program called “HyperTerminal” which
does just that, otherwise, you can download a terminal emulator called “TeraTerm” from
http://ttssh2.sourceforge.jp/index.html.en or “RealTerm” from http://realterm.sourceforge.net/
With the terminal emulator installed and running, press “Reset” on RenBED; you should hear Windows informing you
that the device has connected; now you can connect the terminal emulator to the appropriate serial port, look for the
one called “MBED Virtual Serial Port”. Once connected, after approximately 10 seconds, RenBED will ask you what
your name is… If this does not happen; shut down the terminal emulator, reset RenBED and try again…
Output is:
What is your name?
Jon
What are you doing Jon?
/*******************************************************************************
* This program demonstrates how RenBED can operate the keyboard *
* *
* Jon Fuge *
* V1.0 13/12/2013 First issue of code *
*******************************************************************************/
#include "mbed.h"
#include "USBKeyboard.h"
//LED segment A: NUM_LOCK
//LED segment B: CAPS_LOCK
//LED segment C: SCROLL_LOCK
BusOut leds(P1_23, P1_28, P0_16);
USBKeyboard keyboard;
int main(void) {
for (;;) {
keyboard.mediaControl(KEY_VOLUME_DOWN); // Turn the volume down
keyboard.printf("Hello World from RenBED \r\n"); // Send a message
keyboard.keyCode('s', KEY_CTRL); // Send CTRL ‐ S
keyboard.keyCode(KEY_CAPS_LOCK); // Toggle CAPS LOCK
wait(1); // Wait for 1 second
leds = keyboard.lockStatus(); // Display LED status of keyboard
}
}
/*******************************************************************************
* This program demonstrates the use of mouse and keyboard concurrently *
* *
* Jon Fuge *
* V1.0 13/12/2013 First issue of code *
*******************************************************************************/
#include "mbed.h"
#include "USBMouseKeyboard.h"
#define mDegreeToRadian 3.14/180
#define RADIUS 10
//LED segment A: NUM_LOCK
//LED segment B: CAPS_LOCK
//LED segment C: SCROLL_LOCK
BusOut leds(P1_23, P1_28, P0_16);
//USBMouseKeyboard
USBMouseKeyboard key_mouse;
int main(void) {
int16_t i16_X;
int16_t i16_Y;
int32_t i32_Angle = 0; // set the start angle
for (;;) {
key_mouse.mediaControl(KEY_VOLUME_UP); // Turn the volume down
key_mouse.keyCode(KEY_CAPS_LOCK); // Toggle CAPS LOCK
key_mouse.keyCode(KEY_SCROLL_LOCK); // Toggle SCROLL LOCK
i16_X = cos((double)i32_Angle * mDegreeToRadian) * RADIUS; // calculate x offset
i16_Y = sin((double)i32_Angle * mDegreeToRadian) * RADIUS; // calculate y offset
key_mouse.move(i16_X, i16_Y); // send a message to move the mouse cursor
i32_Angle += 3; // move to the next angle of annoyance
wait(.1);
leds = key_mouse.lockStatus();
}
}
/*******************************************************************************
* This program demonstrates the use of a USB HID with descriptors *
* *
* Jon Fuge *
* V1.0 13/12/2013 First issue of code *
*******************************************************************************/
#include "mbed.h"
#include "USBHID.h"
//We declare a USBHID device. By default input and output reports are 64 bytes long.
USBHID hid(8, 8);
Serial pc(USBTX, USBRX);
//This report will contain data to be sent
HID_REPORT send_report;
HID_REPORT recv_report;
DigitalOut l1(LED1);
int main(void) {
send_report.length = 8;
for (;;) {
//Fill the report
for (int i = 0; i < send_report.length; i++)
send_report.data[i] = rand() & 0xff;
//Send the report
hid.send(&send_report);
//try to read a msg
if(hid.readNB(&recv_report)) {
l1 = !l1;
for(int i = 1; i < recv_report.length; i++) {
pc.printf("%d ", recv_report.data[i]);
}
pc.printf("\r\n");
}
}
}
The subject of USB HID requires expert programming knowledge and will not be covered further in this document.
/*******************************************************************************
* This program receives audio from the PC then writes this data back to the *
* serial port *
* *
* Jon Fuge *
* V1.0 16/12/2013 First issue of code *
*******************************************************************************/
#include "mbed.h"
#include "USBAudio.h"
Serial pc(USBTX, USBRX);
// frequency: 48 kHz
#define FREQ 48000
// 1 channel: mono
#define NB_CHA 1
// length of an audio packet: each ms, we receive 48 * 16bits ‐>48 * 2 bytes.
#define AUDIO_LENGTH_PACKET 48 * 2 * 1
// USBAudio
USBAudio audio(FREQ, NB_CHA);
int main() {
int16_t buf[AUDIO_LENGTH_PACKET/2];
for (;;) {
// read an audio packet
audio.read((uint8_t *)buf);
// print packet received
pc.printf("recv: ");
for(int i = 0; i < AUDIO_LENGTH_PACKET/2; i++) {
pc.printf("%d ", buf[i]);
}
pc.printf("\r\n");
}
} Change the default sound board
control panel
Hardware and Sound
Manage audio device in the Sound section
Select the Mbed Audio device and press Set default
/*******************************************************************************
* This program writes music to the PC Midi interpreter, then reads data back *
* and displays the key codes on the seven segment displays **
*
* Jon Fuge *
* V1.0 16/12/2013 First issue of code *
*******************************************************************************/
#include "mbed.h"
#include "USBMIDI.h"
#include "SevenSegLed.h"
#define mUnits D_7seg[1] // "mUnits" will be substiuted for "D_7seg[1]"
#define mTens D_7seg[0] // "mTens" will be substiuted for "D_7seg[0]"
#define mDot D_dot[1] // "mDot" will be substiuted for "D_dot[1]"
SevenSegLed segmentled(0, 1, P1_23, P1_28, P0_16, P1_31, P1_13, P1_16, P1_19, P0_23, p21, P1_25);
uint8_t D_7seg[2] = {0, 0}; // number (0x00:"0", ... , 0x09:"9", 0x0A:"A", ... , 0x0F:"F", other:" ")
uint8_t D_dot[2] = {0, 0}; // dotpoint. (0:off 1:on)
//USBMIDI object
USBMIDI midi;
void show_message(MIDIMessage msg)
{
switch (msg.type()) {
case MIDIMessage::NoteOnType:
mUnits = msg.key() % 16;
mTens = msg.key() / 16;
break;
case MIDIMessage::NoteOffType:
default:
mUnits = 0x11;
mTens = 0x11;
}
}
int main()
{
// call back for messages received
midi.attach(show_message);
for (;;) {
for(int i=48; i<83; i++) { // send some messages!
midi.write(MIDIMessage::NoteOn(i));
wait(0.1);
midi.write(MIDIMessage::NoteOff(i));
wait(0.1);
}
for (;;) {
segmentled.SevenSegLed_main(D_7seg, D_dot); // Keep the displays multiplexed.
}
}
}
Although I have put pointers in an orange box (expert skills), pointers are very useful and you are encouraged to learn
how to use them. The example below shows how pointers are used.
/*******************************************************************************
* This program demonstrates the use of pointers *
* *
* Jon Fuge *
* V1.0 25/11/2013 First issue of code *
*******************************************************************************/
#include "mbed.h"
#include "USBSerial.h"
USBSerial serial; // Virtual serial port over USB. Use Teraterm as the interface
int main(void) {
char cBox1 = 5;
char cBox2 = 10; // Declare two variables. Orange boxes contain
char *ptr = &cBox1; // Declare a pointer directed to cBox1 “expert” information.
wait (10); // Wait 10 seconds to connect port
serial.printf("cBox1:%i, cBox2:%i, *ptr:%i\n\r", cBox1, cBox2, *ptr);
cBox2 = cBox1; // cBox2 was 10, but is now 5
serial.printf("cBox1:%i, cBox2:%i, *ptr:%i\n\r", cBox1, cBox2, *ptr);
cBox1 = 15; // cBox1 was 5, but is now 15
serial.printf("cBox1:%i, cBox2:%i, *ptr:%i\n\r", cBox1, cBox2, *ptr);
// cBox2 will still report 5, but *ptr now reports 15
for(;;) {} // Loop forever Output is:
} cBox1:5, cBox2:10, *ptr:5
cBox1:5, cBox2:5, *ptr:5
cBox1:15, cBox2:5, *ptr:15
typedef
typedef allows you to create an alias or synonym of an existing type (or types). stdint.h uses typedef to create new more
readable types…
/*******************************************************************************
* This program demonstrates the use of structures *
* *
* Jon Fuge *
* V1.0 25/11/2013 First issue of code *
*******************************************************************************/
#include "mbed.h"
typedef unsigned short myword; // Declare myword as a new type
int main() {
myword mwAddress; // Declare variables with the new type
mwAddress = 600;
for(;;) {} // Loop forever
}
#define
#define lets you make a macro which substitutes a set of commands for just one.
/*******************************************************************************
* This program demonstrates the use of #define *
* Jon Fuge V1.0 26/11/2013 First issue of code *
*******************************************************************************/
#include "mbed.h"
#include "USBSerial.h"
#define Position1 Position.iX = 1; Position.iY = 2 // without parameters
#define SetPosition(NewX, NewY) Position.iX = NewX; Position.iY = NewY // with parameters
struct coordXY { int iX; int iY; }; // Define a new structure
int main() {
USBSerial serial; // Virtual serial port over USB. Use Teraterm as the interface
coordXY Position; // Declare variable with the new structure
wait (10); // Wait 10 seconds to connect port
Position1; // Sets Position to Position1
serial.printf("Position.iX:%i, Position.iY:%i\n\r", Position.iX, Position.iY);
SetPosition( 9, 6 ); // Directly load Position1 from Position2
serial.printf("Position.iX:%i, Position.iY:%i\n\r", Position.iX, Position.iY);
for(;;) {} // Loop forever Output is:
} Position1.iX:1, Position1.iY:2
Position1.iX:9, Position1.iY:6
Word
16‐bit number
Lo Hi
2 x 8‐bit numbers
From the table, we can see that if the number is odd, “Bit0” must be 1, if it is even, “Bit0” must be 0.
/*******************************************************************************
* This program demonstrates determines if a number is odd or even *
* Jon Fuge V1.0 26/11/2013 First issue of code *
*******************************************************************************/
#include "mbed.h"
#include "USBSerial.h"
USBSerial serial; //Virtual serial port over USB. Use Teraterm as the interface
int main() {
char cMyNumber = 53; // Set it to an odd number
wait (10); // Wait 10 seconds to connect port
if ((cMyNumber & 0x01) == 1)
serial.printf("%i is odd\n\r", cMyNumber);
else
serial.printf("%i is even\n\r", cMyNumber);
for(;;) {} // Loop forever Output is:
} 53 is odd
This code does indeed work and generates the expected result that 53 is an odd number, but we need to do a bitwise
AND calculation to determine if it is odd or even.
/*******************************************************************************
* This program demonstrates determines if a number is odd or even *
* Jon Fuge V1.0 26/11/2013 First issue of code *
*******************************************************************************/
#include "mbed.h"
#include "USBSerial.h"
union byte // Define new type “byte”
{
char Byte; // Use this to map a byte
struct {
char Odd: 1; // this is the same as Bit0
char Others: 7; // Just fill the rest of the bits
};
};
USBSerial serial; // Virtual serial port over USB. Use Teraterm as the interface
int main() {
byte cMyNumber; // Declare variable cMyNumber
cMyNumber.Byte = 53; // Set it to an odd number
wait (10); // Wait 10 seconds to connect port
if (cMyNumber.Odd == 1)
serial.printf("%i is odd\n\r", cMyNumber.Byte);
else
serial.printf("%i is even\n\r", cMyNumber.Byte);
for(;;) {} // Loop forever Output is:
} 53 is odd
The second example looks like there is more code, but it is more readable, and produces efficient code.
/*******************************************************************************
* This program demonstrates determines if a number is odd or even *
* Jon Fuge V1.0 26/11/2013 First issue of code *
*******************************************************************************/
#include "mbed.h"
#include "USBSerial.h"
union byte // Define new type “byte”
{
char Byte; // Use this to map a byte
struct {
char Bit0: 1; // map individual
char Bit1: 1; // bits onto the
char Bit2: 1; // mapped byte.
char Bit3: 1;
char Bit4: 1;
char Bit5: 1;
char Bit6: 1;
char Bit7: 1;
};
};
USBSerial serial; // Virtual serial port over USB. Use Teraterm as the interface
int main() {
byte cMyNumber; // Declare variable cMyNumber
cMyNumber.Byte = 53; // Set it to an odd number
wait (10); // Wait 10 seconds to connect port
if (cMyNumber.Bit0 == 1)
serial.printf("%i is odd\n\r", cMyNumber.Byte);
else
serial.printf("%i is even\n\r", cMyNumber.Byte);
for(;;) {} // Loop forever
}
Output is:
53 is odd
The last piece of code has not added any revelations, but it does provide a few useful definitions so you can now
access each individual bit in a byte, which is a feature that is often used in embedded systems.
Code block Condition
Condition
Condition
Code block
Code block
Rest of code
Increment Rest of code
do while (Condition)
{ {
Rest of code Code block Code block
} while (Condition) }
For( Initialise; Condition; Increment) Rest of code Rest of code
{ Tests after! Tests before!
Code block
}
Rest of code break continue
Tests before! allows you to exit a while, allows you to skip to the
do, or for statement. next loop of a while, do, or
for statement.
/****************************** /******************************
*This program determines if * *This program determines if *
*the temperature is just right* *the temperature is just right*
*cold, too cold, warm or too * *cold, too cold, warm or too *
*warm using “if” * *warm using “switch *
*Jon Fuge * *Jon Fuge *
*V1.0 2/12/2013 First issue * *V1.0 2/12/2013 First issue *
******************************/ ******************************/
#include "mbed.h" #include "mbed.h"
#include "USBSerial.h" #include "USBSerial.h"
#define Send serial.printf #define Send serial.printf
USBSerial serial; USBSerial serial;
// Declare constants // Declare constants
const char cCOLD = 23; const char cCOLD = 23;
const char cJUST_RIGHT = 24; const char cJUST_RIGHT = 24;
const char cWARM = 25 ; const char cWARM = 25;
// declare prototype for GetTemperature. // declare prototype for GetTemperature.
char GetTemperature(void); char GetTemperature(void);
int main() { int main() {
char cTemperature = GetTemperature(); char cTemperature = GetTemperature();
wait (5); // Wait 5 seconds to connect wait (5); // Wait 5 seconds to connect
if (cTemperature == cCOLD) { switch (cTemperature) {
Send("Cold\n\r"); case cCOLD: Send("Cold\n\r");
} else { break;
if (cTemperature == cWARM) { case cWARM: Send("Warm\n\r");
Send("Warm\n\r"); break;
} else { case cJUST_RIGHT: Send("Just right\n\r");
if (cTemperature == cJUST_RIGHT) { break;
Send("Just right\n\r"); default: Send("Too hot or too\
} else { cold\n\r");
Send("Too hot or too cold\n\r"); }
}
}
break
}
char GetTemperature(void)
char GetTemperature(void) { exits the switch
{ return (cJUST_RIGHT); statement.
return (cJUST_RIGHT); }
}
switch can be used to replace a series of sequential ifs, however, if can evaluate more than just “Equal to” as can
be seen in the table of “Relational operators” below; also, “Relational operators” can be linked to make more powerful
conditions with “Logical operators”
The use of in-line assembly language is frowned upon because this stops your code from being “transportable” so a large
amount of effort would be required to transfer the code to another processor; it also makes the code difficult to read by
most programmers.
If anyone suggests using “machine code” or “assembly language”, please offer them a nice sweet cup of tea and sit down
and reminisce about the “good old days” with them, they will probably want to discuss the obvious benefits of punched
card for data storage and the use of dekatrons as a debugger. If they still think there is a need for machine code due to
using an 8 bit processor and slow clocks, it would be a good time to share the benefits of a modern ARM processor.
goto
goto allows you to interrupt the normal processing of your code and jump to another location. the use of goto is frowned
upon and leads to difficult to read and manage code so is generally not used except as an error trap to interrupt the
normal flow of a program.
/*******************************************************************************
* This program demonstrates the use of goto *
* *
* Jon Fuge *
* V1.0 3/12/2013 First issue of code *
*******************************************************************************/
#include "USBSerial.h"
int main() {
BadLabel:
// code would go here
goto BadLabel;
}
The use of goto falls into a similar category as asm, its use should be avoided at all costs and doing so will lead to more
readable code which can be re-used.
The difference between functions and procedures is that a function has a type before its declaration so it can return
a value when it terminates. Procedures have a void before the declaration meaning it does not return a value.
Procedures and functions can have parameters passed to them. To pass a parameter, we add the type and name of
the parameter between the brackets; if we want to add more parameters we do so by separating them with commas.
/*******************************************************************************
* This program demonstrates the use of functions and procedures *
* Jon Fuge V1.0 26/11/2013 First issue of code *
*******************************************************************************/
#include "mbed.h"
#include "USBSerial.h"
// Prototype functions and procedures are always declared before main!
int GetNumberFromUser(void); // Get the value from the user
int SquareNumber(int iX); // Get the square of x
void SendSquareToUser(int iX); // Output our square to the user
USBSerial serial; // Virtual serial port over USB. Use Teraterm as the interface
int main() {
int UserNumber; A function returns a
int SquareUserNumber; value, a procedure
doesn’t.
wait (5); // Wait 5 seconds to connect port
for(;;) // start an endless loop.
{
UserNumber = GetNumberFromUser();
SquareUserNumber = SquareNumber(UserNumber); Tip… Use tabs or
SendSquareToUser(SquareUserNumber);
}
3 spaces to indent
} your code making
it more readable.
int GetNumberFromUser(void)
{
char buf[128]; // A char array is also a string!
for (;;) { // Keep looping until we get a valid number
serial.printf("Enter a number between 0 & 9:\r\n");
serial.scanf("%s", buf); // Receive message from USB serial port
if ((buf[0] >= '0') && (buf[0] <= '9')) // We can only process single digit numbers
{
serial.printf("%c is a great choice!\r\n", buf[0]);
return (buf[0] ‐ '0'); // Convert number from ASCII to decimal
}
serial.printf("I didn't like that, try again!\r\n");
}
}
int SquareNumber(int iX)
{
return (iX*iX); // return the value of x*x (x squared).
}
void SendSquareToUser(int iX) Output is:
{ Enter a number between 0 & 9:
serial.printf("The square is %i\r\n", iX); 5 is a great choice!
} The square is 25
Modules can be divided into two parts, the header is stored in a .h file which contains all the public parts such as
macros, typedef’s, function prototypes and constants. The private parts of a module are stored in a .cpp file.
Header Files
It is very common for headers to include other headers which can lead to problems when multiple instances of the
same definition exist; this can be overcome by the addition of the following code …
/*******************************************************************************
* This is an example header file *
* *
* Jon Fuge *
* V1.0 3/12/2013 First issue of code *
*******************************************************************************/
#ifndef UNIQUE_MACRO_NAME
#define UNIQUE_MACRO_NAME
// Add the body of your header here
#endif
The body of the header is only seen by the compiler if UNIQUE_MACRO_NAME is not defined, then it is immediately
defined.
To demonstrate the use of modules and how easy they are to create, we will look at the example on the previous page
introducing functions and procedures splitting the original “main.c” file into three new files “UserNumber.h”,
“UserNumber.cpp” and a cut down version of our original “main.c”. Although this example does not yield any
reusable functions, it does demonstrate how we could use the files “UserNumber.h” and “UserNumber.cpp” again in
future programs by copying the header and .cpp file into a new program and using #include "UserNumber.h" to
reference them…
UserNumber.h:
/*******************************************************************************
* This header groups the user / number handling functions *
* *
* Jon Fuge *
* V1.0 3/12/2013 First issue of code *
*******************************************************************************/
#ifndef USERNUMBER
#define USERNUMBER
int GetNumberFromUser(void); // Get the value from the user
int SquareNumber(int iX); // Get the square of x
void SendSquareToUser(int iX); // Output our square to the user
#endif
main.cpp:
/*******************************************************************************
* This program demonstrates the use of functions, procedures and modules *
* Jon Fuge *
* V1.0 3/12/2013 First issue of code *
*******************************************************************************/
#include "mbed.h"
#include "UserNumber.h"
int main() {
wait (5); // Wait 5 seconds to connect port
int UserNumber;
int SquareUserNumber;
for(;;) // start an endless loop.
{
UserNumber = GetNumberFromUser();
SquareUserNumber = SquareNumber(UserNumber);
SendSquareToUser(SquareUserNumber);
}
}
If you have not previously opened a project, you can click on "import a program" (in the middle of the screen);
otherwise, you can click on the "import button".
Tip: if using internet explorer, pressing the F11 button will make this full screen giving you the maximum available
space to use.
You will be given a window to edit the program details, we’ll leave it set to the defaults, click the “Import” button
For this workshop, we’ll change the output pin from “LED1” to use DIP36 on RenBED (P0_21)
Edit Line 3 and replace “LED1” with “P0_21”.
For a new account, you probably do not have a device selected; the compiler will need to know this so your
program can be compiled into a form that RenBED can use.
If you have not previously opened a project you can click on "create a new one" (in the middle of the screen);
otherwise, you can click on the "New" button (if you are asked, you want a new program. A useful tip (if using
internet explorer, pressing the F11 button will make this full screen giving you the maximum available space to
use).
Your empty project has been created, and it is just that, empty!
Now we have the code entered, but we need to add the “mbed.h” library to our program or it will not compile.
The top “mbed” file with thousands of previous imports is the one we want to use. Click on “mbed” to highlight
it, then click “Import!”. (Tip, we are likely to use this library often, by clicking on the next to “mbed” will
bookmark it to make it easy to find in the future).
Click “Import”, in the window, Leave Import name as “mbed”, Target Path should be “ReadButton”.
If you have not already done so, you will need to select a target device.
Return to the compiler by clicking “Compiler” at the top right of the screen.
Now you can compile your first program... Click "Compile" in the middle of the top buttons.
Well done, you are now set up to use mbed and have compiled your program!
You will have completed the above steps and compiled your project, you should either be prompted for a place to
save your ".bin" file, or it has gone off to the downloads folder.
Before you can do anything, you will need to connect RenBED to your PC.
o Connect RenBED to your PC using the USB lead.
o Put RenBED into "Programming mode", press the left button with "ISP" next to it, a yellow LED will
illuminate.
o Your PC will recognize RenBED as a USB pen drive with the label "CRP DISABLD". Make a note of the
drive letter, for me it is "O:"
If your browser has saved the ".bin" file to the "downloads" folder, you will need to copy the file from there.
o Click on the browser window, then press CTRL-J.