You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

102 lines
2.7KB

  1. // Copyright 2011 Peter Kvitek
  2. //
  3. // Author: Peter Kvitek (pete@kvitek.com)
  4. //
  5. // This program is free software: you can redistribute it and/or modify
  6. // it under the terms of the GNU General Public License as published by
  7. // the Free Software Foundation, either version 3 of the License, or
  8. // (at your option) any later version.
  9. // This program is distributed in the hope that it will be useful,
  10. // but WITHOUT ANY WARRANTY; without even the implied warranty of
  11. // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  12. // GNU General Public License for more details.
  13. // You should have received a copy of the GNU General Public License
  14. // along with this program. If not, see <http://www.gnu.org/licenses/>.
  15. //
  16. // -----------------------------------------------------------------------------
  17. //
  18. // Serial debug output. Supports USART and software serial, both vanilla and buffered.
  19. //
  20. // Overrides stdout so printf("Hello world"), putc() etc. all do the right thing.
  21. //
  22. // * USART output declaration:
  23. //
  24. // DebugOutput< Serial<SerialPort0, 57600, DISABLED, POLLED> > dbg;
  25. //
  26. // * Software serial declaration: (see software_serial.h)
  27. //
  28. // DebugOutput< SoftwareSerialOutput< Gpio<PortD, 1>, 57600> > dbg;
  29. //
  30. // * Buffered software serial declaration:
  31. //
  32. // typedef BufferedSoftwareSerialOutput< Gpio<PortD, 1>, 31250, 2400, 32> DbgOutput;
  33. //
  34. // DebugOutput<DbgOutput> dbg;
  35. //
  36. // void InitTimer2() {
  37. // Timer<2>::set_prescaler(3);
  38. // Timer<2>::set_mode(TIMER_CTC);
  39. // TIMSK2|= (1 << OCIE2A);
  40. // OCR2A = 19; // for prescaler 32 @ 20MHz
  41. // Timer<2>::Start();
  42. // }
  43. //
  44. // ISR(TIMER2_COMPA_vect)
  45. // {
  46. // DbgOutput::Tick(); // called at 31250 kHz
  47. // }
  48. #ifndef AVRLIB_DEBUG_OUTPUT_H_
  49. #define AVRLIB_DEBUG_OUTPUT_H_
  50. #include <stdio.h>
  51. #include <avr/io.h>
  52. #include "avrlib/serial.h"
  53. namespace avrlib {
  54. template<typename SerialT, bool ensureCRLF = false>
  55. class DebugOutput {
  56. public:
  57. DebugOutput() { }
  58. static void Init() {
  59. SerialT::Init();
  60. stdout = &dbg_stdout_;
  61. }
  62. static inline void Write(char c) {
  63. if (ensureCRLF && c == '\n') {
  64. SerialT::Write('\r');
  65. }
  66. SerialT::Write(c);
  67. }
  68. static inline void Write(char* s) {
  69. while (*s) {
  70. Write(*s++);
  71. }
  72. }
  73. private:
  74. static FILE dbg_stdout_;
  75. static int dbg_putchar(char c, FILE* stream) {
  76. Write(c);
  77. return 0;
  78. }
  79. DISALLOW_COPY_AND_ASSIGN(DebugOutput);
  80. };
  81. // Static variables created for each instance
  82. template<typename SerialT, bool ensureCRLF>
  83. FILE DebugOutput<SerialT, ensureCRLF>::dbg_stdout_ =
  84. { 0, 0, _FDEV_SETUP_WRITE, 0, 0, DebugOutput<SerialT, ensureCRLF>::dbg_putchar, NULL, 0 };
  85. } // namespace avrlib
  86. #endif // AVRLIB_DEBUG_OUTPUT_H_