diff --git a/app/src/processing/app/Preferences.java b/app/src/processing/app/Preferences.java index 06f48f2bf..640cb2e1f 100644 --- a/app/src/processing/app/Preferences.java +++ b/app/src/processing/app/Preferences.java @@ -139,7 +139,7 @@ public class Preferences { "lv", "lt", "mr", - "no", + "no_nb", "fa", "pl", "pt_br", diff --git a/app/src/processing/app/SerialMonitor.java b/app/src/processing/app/SerialMonitor.java index 6eebf539e..1f34e8f7e 100644 --- a/app/src/processing/app/SerialMonitor.java +++ b/app/src/processing/app/SerialMonitor.java @@ -127,10 +127,10 @@ public class SerialMonitor extends JFrame implements MessageConsumer { serialRates = new JComboBox(); for (int i = 0; i < serialRateStrings.length; i++) - serialRates.addItem(serialRateStrings[i] + _(" baud")); + serialRates.addItem(serialRateStrings[i] + " " + _("baud")); serialRate = Preferences.getInteger("serial.debug_rate"); - serialRates.setSelectedItem(serialRate + _(" baud")); + serialRates.setSelectedItem(serialRate + " " + _("baud")); serialRates.addActionListener(new ActionListener() { public void actionPerformed(ActionEvent event) { String wholeString = (String) serialRates.getSelectedItem(); diff --git a/app/src/processing/app/Sketch.java b/app/src/processing/app/Sketch.java index 3f19cd3a3..0293b622f 100644 --- a/app/src/processing/app/Sketch.java +++ b/app/src/processing/app/Sketch.java @@ -1369,6 +1369,9 @@ public class Sketch { for (SketchCode sc : code) { if (sc.isExtension("ino") || sc.isExtension("pde")) { sc.setPreprocOffset(bigCount); + // These #line directives help the compiler report errors with + // correct the filename and line number (issue 281 & 907) + bigCode.append("#line 1 \"" + sc.getFileName() + "\"\n"); bigCode.append(sc.getProgram()); bigCode.append('\n'); bigCount += sc.getLineCount(); @@ -1541,54 +1544,16 @@ public class Sketch { public RunnerException placeException(String message, String dotJavaFilename, int dotJavaLine) { - int codeIndex = 0; //-1; - int codeLine = -1; - -// System.out.println("placing " + dotJavaFilename + " " + dotJavaLine); -// System.out.println("code count is " + getCodeCount()); - - // first check to see if it's a .java file - for (int i = 0; i < getCodeCount(); i++) { - SketchCode code = getCode(i); - if (!code.isExtension(getDefaultExtension())) { - if (dotJavaFilename.equals(code.getFileName())) { - codeIndex = i; - codeLine = dotJavaLine; - return new RunnerException(message, codeIndex, codeLine); - } - } - } - - // If not the preprocessed file at this point, then need to get out - if (!dotJavaFilename.equals(name + ".cpp")) { - return null; - } - - // if it's not a .java file, codeIndex will still be 0 - // this section searches through the list of .pde files - codeIndex = 0; - for (int i = 0; i < getCodeCount(); i++) { - SketchCode code = getCode(i); - - if (code.isExtension(getDefaultExtension())) { -// System.out.println("preproc offset is " + code.getPreprocOffset()); -// System.out.println("looking for line " + dotJavaLine); - if (code.getPreprocOffset() <= dotJavaLine) { - codeIndex = i; -// System.out.println("i'm thinkin file " + i); - codeLine = dotJavaLine - code.getPreprocOffset(); - } - } - } - // could not find a proper line number, so deal with this differently. - // but if it was in fact the .java file we're looking for, though, - // send the error message through. - // this is necessary because 'import' statements will be at a line - // that has a lower number than the preproc offset, for instance. -// if (codeLine == -1 && !dotJavaFilename.equals(name + ".java")) { -// return null; -// } - return new RunnerException(message, codeIndex, codeLine); + // Placing errors is simple, because we inserted #line directives + // into the preprocessed source. The compiler gives us correct + // the file name and line number. :-) + for (int codeIndex = 0; codeIndex < getCodeCount(); codeIndex++) { + SketchCode code = getCode(codeIndex); + if (dotJavaFilename.equals(code.getFileName())) { + return new RunnerException(message, codeIndex, dotJavaLine); + } + } + return null; } diff --git a/app/src/processing/app/debug/Compiler.java b/app/src/processing/app/debug/Compiler.java index 284550faa..c97a1c268 100644 --- a/app/src/processing/app/debug/Compiler.java +++ b/app/src/processing/app/debug/Compiler.java @@ -54,6 +54,7 @@ public class Compiler implements MessageConsumer { private PreferencesMap prefs; private boolean verbose; + private boolean sketchIsCompiled; private RunnerException exception; @@ -71,6 +72,7 @@ public class Compiler implements MessageConsumer { throws RunnerException { sketch = _sketch; verbose = _verbose; + sketchIsCompiled = false; objectFiles = new ArrayList(); prefs = createBuildPreferences(_buildPath, _primaryClassName); @@ -87,6 +89,7 @@ public class Compiler implements MessageConsumer { // 1. compile the sketch (already in the buildPath) sketch.setCompilingProgress(30); compileSketch(includePaths); + sketchIsCompiled = true; // 2. compile the libraries, outputting .o files to: // // Doesn't really use configPreferences @@ -339,10 +342,8 @@ public class Compiler implements MessageConsumer { boolean compiling = true; while (compiling) { try { - if (in.thread != null) - in.thread.join(); - if (err.thread != null) - err.thread.join(); + in.join(); + err.join(); result = process.waitFor(); //System.out.println("result is " + result); compiling = false; @@ -430,7 +431,7 @@ public class Compiler implements MessageConsumer { if (pieces[3].trim().equals("'Udp' was not declared in this scope")) { error = _("The Udp class has been renamed EthernetUdp."); msg = _("\nAs of Arduino 1.0, the Udp class in the Ethernet library " + - "has been renamed to EthernetClient.\n\n"); + "has been renamed to EthernetUdp.\n\n"); } if (pieces[3].trim().equals("'class TwoWire' has no member named 'send'")) { @@ -455,14 +456,20 @@ public class Compiler implements MessageConsumer { //msg = _("\nThe 'Keyboard' class is only supported on the Arduino Leonardo.\n\n"); } - RunnerException e = sketch.placeException(error, pieces[1], PApplet.parseInt(pieces[2]) - 1); + RunnerException e = null; + if (!sketchIsCompiled) { + // Place errors when compiling the sketch, but never while compiling libraries + // or the core. The user's sketch might contain the same filename! + e = sketch.placeException(error, pieces[1], PApplet.parseInt(pieces[2]) - 1); + } // replace full file path with the name of the sketch tab (unless we're // in verbose mode, in which case don't modify the compiler output) if (e != null && !verbose) { SketchCode code = sketch.getCode(e.getCodeIndex()); - String fileName = code.isExtension(sketch.getDefaultExtension()) ? code.getPrettyName() : code.getFileName(); - s = fileName + ":" + e.getCodeLine() + ": error: " + pieces[3] + msg; + String fileName = (code.isExtension("ino") || code.isExtension("pde")) ? code.getPrettyName() : code.getFileName(); + int lineNum = e.getCodeLine() + 1; + s = fileName + ":" + lineNum + ": error: " + pieces[3] + msg; } if (exception == null && e != null) { diff --git a/app/src/processing/app/debug/MessageSiphon.java b/app/src/processing/app/debug/MessageSiphon.java index 79a0920d5..12b1f993b 100644 --- a/app/src/processing/app/debug/MessageSiphon.java +++ b/app/src/processing/app/debug/MessageSiphon.java @@ -85,8 +85,15 @@ public class MessageSiphon implements Runnable { } } - + // Wait until the MessageSiphon thread is complete. + public void join() throws java.lang.InterruptedException { + // Grab a temp copy in case another thread nulls the "thread" + // member variable + Thread t = thread; + if (t != null) t.join(); + } + public Thread getThread() { return thread; -} + } } diff --git a/app/src/processing/app/debug/Sizer.java b/app/src/processing/app/debug/Sizer.java index 2de116cb2..89bfe5ee0 100644 --- a/app/src/processing/app/debug/Sizer.java +++ b/app/src/processing/app/debug/Sizer.java @@ -60,10 +60,8 @@ public class Sizer implements MessageConsumer { boolean running = true; while(running) { try { - if (in.thread != null) - in.thread.join(); - if (err.thread != null) - err.thread.join(); + in.join(); + err.join(); r = process.waitFor(); running = false; } catch (InterruptedException intExc) { } diff --git a/app/src/processing/app/preproc/PdePreprocessor.java b/app/src/processing/app/preproc/PdePreprocessor.java index 2b4f03e85..4f848c922 100644 --- a/app/src/processing/app/preproc/PdePreprocessor.java +++ b/app/src/processing/app/preproc/PdePreprocessor.java @@ -205,7 +205,7 @@ public class PdePreprocessor { for (int i = 0; i < prototypes.size(); i++) { out.print(prototypes.get(i) + "\n"); } - + out.println("#line 1"); out.print(program.substring(prototypeInsertionPoint)); } diff --git a/app/src/processing/app/tools/Archiver.java b/app/src/processing/app/tools/Archiver.java index cb282ed69..67c848a17 100755 --- a/app/src/processing/app/tools/Archiver.java +++ b/app/src/processing/app/tools/Archiver.java @@ -56,7 +56,7 @@ public class Archiver implements Tool { numberFormat.setGroupingUsed(false); // no commas numberFormat.setMinimumIntegerDigits(digits); - dateFormat = new SimpleDateFormat(_("yyMMdd")); + dateFormat = new SimpleDateFormat("yyMMdd"); } diff --git a/build/shared/examples/02.Digital/tonePitchFollower/tonePitchFollower.ino b/build/shared/examples/02.Digital/tonePitchFollower/tonePitchFollower.ino index 2bdf0df26..e74c7b343 100644 --- a/build/shared/examples/02.Digital/tonePitchFollower/tonePitchFollower.ino +++ b/build/shared/examples/02.Digital/tonePitchFollower/tonePitchFollower.ino @@ -9,8 +9,8 @@ * 4.7K resistor on analog 0 to ground created 21 Jan 2010 - modified 9 Apr 2012 - by Tom Igoe + modified 31 May 2012 + by Tom Igoe, with suggestion from Michael Flynn This example code is in the public domain. @@ -29,10 +29,11 @@ void loop() { int sensorReading = analogRead(A0); // print the sensor reading so you know its range Serial.println(sensorReading); - // map the pitch to the range of the analog input. + // map the analog input range (in this case, 400 - 1000 from the photoresistor) + // to the output pitch range (120 - 1500Hz) // change the minimum and maximum input numbers below // depending on the range your sensor's giving: - int thisPitch = map(sensorReading, 400, 1000, 100, 1000); + int thisPitch = map(sensorReading, 400, 1000, 120, 1500); // play the pitch: tone(9, thisPitch, 10); diff --git a/hardware/arduino/avr/cores/arduino/Print.cpp b/hardware/arduino/avr/cores/arduino/Print.cpp index e541a6ce7..711251c8a 100755 --- a/hardware/arduino/avr/cores/arduino/Print.cpp +++ b/hardware/arduino/avr/cores/arduino/Print.cpp @@ -226,6 +226,9 @@ size_t Print::printFloat(double number, uint8_t digits) { size_t n = 0; + if (isnan(number)) return print("nan"); + if (isinf(number)) return print("inf"); + // Handle negative numbers if (number < 0.0) { diff --git a/hardware/arduino/avr/cores/arduino/Print.h b/hardware/arduino/avr/cores/arduino/Print.h index 1af6b723f..dc7615087 100755 --- a/hardware/arduino/avr/cores/arduino/Print.h +++ b/hardware/arduino/avr/cores/arduino/Print.h @@ -46,7 +46,10 @@ class Print void clearWriteError() { setWriteError(0); } virtual size_t write(uint8_t) = 0; - size_t write(const char *str) { return write((const uint8_t *)str, strlen(str)); } + size_t write(const char *str) { + if (str == NULL) return 0; + return write((const uint8_t *)str, strlen(str)); + } virtual size_t write(const uint8_t *buffer, size_t size); size_t print(const __FlashStringHelper *); diff --git a/hardware/arduino/avr/cores/arduino/USBAPI.h b/hardware/arduino/avr/cores/arduino/USBAPI.h index d5abdb690..eb2e5937d 100644 --- a/hardware/arduino/avr/cores/arduino/USBAPI.h +++ b/hardware/arduino/avr/cores/arduino/USBAPI.h @@ -39,6 +39,7 @@ public: virtual int read(void); virtual void flush(void); virtual size_t write(uint8_t); + using Print::write; // pull in write(str) and write(buf, size) from Print operator bool(); }; extern Serial_ Serial; diff --git a/hardware/arduino/avr/cores/arduino/WInterrupts.c b/hardware/arduino/avr/cores/arduino/WInterrupts.c index 8f3ec847f..62efc9cad 100644 --- a/hardware/arduino/avr/cores/arduino/WInterrupts.c +++ b/hardware/arduino/avr/cores/arduino/WInterrupts.c @@ -59,6 +59,14 @@ void attachInterrupt(uint8_t interruptNum, void (*userFunc)(void), int mode) { EICRA = (EICRA & ~((1< -SoftwareSerial mySerial(2, 3); // RX, TX +SoftwareSerial mySerial(10, 11); // RX, TX void setup() { - // Open serial communications and wait for port to open: + // Open serial communications and wait for port to open: Serial.begin(57600); - while (!Serial) { + while (!Serial) { ; // wait for serial port to connect. Needed for Leonardo only } - + Serial.println("Goodnight moon!"); // set the data rate for the SoftwareSerial port @@ -43,3 +52,4 @@ void loop() // run over and over if (Serial.available()) mySerial.write(Serial.read()); } + diff --git a/hardware/arduino/avr/libraries/SoftwareSerial/examples/TwoPortReceive/TwoPortReceive.ino b/hardware/arduino/avr/libraries/SoftwareSerial/examples/TwoPortReceive/TwoPortReceive.ino index d9f8f453f..d607ee622 100644 --- a/hardware/arduino/avr/libraries/SoftwareSerial/examples/TwoPortReceive/TwoPortReceive.ino +++ b/hardware/arduino/avr/libraries/SoftwareSerial/examples/TwoPortReceive/TwoPortReceive.ino @@ -16,8 +16,17 @@ * First serial device's TX attached to digital pin 2, RX to pin 3 * Second serial device's TX attached to digital pin 4, RX to pin 5 + Note: + Not all pins on the Mega and Mega 2560 support change interrupts, + so only the following can be used for RX: + 10, 11, 12, 13, 50, 51, 52, 53, 62, 63, 64, 65, 66, 67, 68, 69 + + Not all pins on the Leonardo support change interrupts, + so only the following can be used for RX: + 8, 9, 10, 11, 14 (MISO), 15 (SCK), 16 (MOSI). + created 18 Apr. 2011 - modified 9 Apr 2012 + modified 25 May 2012 by Tom Igoe based on Mikal Hart's twoPortRXExample @@ -26,11 +35,12 @@ */ #include -// software serial #1: TX = digital pin 2, RX = digital pin 3 -SoftwareSerial portOne(2, 3); +// software serial #1: TX = digital pin 10, RX = digital pin 11 +SoftwareSerial portOne(10,11); -// software serial #2: TX = digital pin 4, RX = digital pin 5 -SoftwareSerial portTwo(4, 5); +// software serial #2: TX = digital pin 8, RX = digital pin 9 +// on the Mega, use other pins instead, since 8 and 9 don't work on the Mega +SoftwareSerial portTwo(8,9); void setup() { diff --git a/hardware/arduino/sam/cores/arduino/Print.cpp b/hardware/arduino/sam/cores/arduino/Print.cpp index 123370f4d..4a21176cf 100644 --- a/hardware/arduino/sam/cores/arduino/Print.cpp +++ b/hardware/arduino/sam/cores/arduino/Print.cpp @@ -219,6 +219,9 @@ size_t Print::printFloat(double number, uint8_t digits) { size_t n = 0; + if (isnan(number)) return print("nan"); + if (isinf(number)) return print("inf"); + // Handle negative numbers if (number < 0.0) { diff --git a/hardware/arduino/sam/cores/arduino/Print.h b/hardware/arduino/sam/cores/arduino/Print.h index 1af6b723f..dc7615087 100644 --- a/hardware/arduino/sam/cores/arduino/Print.h +++ b/hardware/arduino/sam/cores/arduino/Print.h @@ -46,7 +46,10 @@ class Print void clearWriteError() { setWriteError(0); } virtual size_t write(uint8_t) = 0; - size_t write(const char *str) { return write((const uint8_t *)str, strlen(str)); } + size_t write(const char *str) { + if (str == NULL) return 0; + return write((const uint8_t *)str, strlen(str)); + } virtual size_t write(const uint8_t *buffer, size_t size); size_t print(const __FlashStringHelper *); diff --git a/hardware/arduino/sam/cores/arduino/USB/USBAPI.h b/hardware/arduino/sam/cores/arduino/USB/USBAPI.h index 0026682c5..fb2baa3d7 100644 --- a/hardware/arduino/sam/cores/arduino/USB/USBAPI.h +++ b/hardware/arduino/sam/cores/arduino/USB/USBAPI.h @@ -57,6 +57,7 @@ public: virtual int read(void); virtual void flush(void); virtual size_t write(uint8_t); + using Print::write; // pull in write(str) and write(buf, size) from Print operator bool(); }; extern Serial_ Serial;