copied everything over from 2012 and removed all of the actual robot code except the drivetrain stuff
git-svn-id: https://robotics.mvla.net/svn/frc971/2013/trunk/src@4078 f308d9b7-e957-4cde-b6ac-9a88185e7312
diff --git a/aos/atom_code/logging/atom_logging.h b/aos/atom_code/logging/atom_logging.h
new file mode 100644
index 0000000..6211e22
--- /dev/null
+++ b/aos/atom_code/logging/atom_logging.h
@@ -0,0 +1,109 @@
+#ifndef AOS_ATOM_CODE_LOGGING_LOGGING_H_
+#define AOS_ATOM_CODE_LOGGING_LOGGING_H_
+
+// IWYU pragma: private, include "aos/common/logging/logging.h"
+
+#ifndef AOS_COMMON_LOGGING_LOGGING_H_
+#error This file may only be #included through common/logging/logging.h!!!
+#endif
+
+#include "aos/aos_core.h"
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+int log_init(const char *name);
+// WARNING: THIS LEAKS MEMORY AND SHARED MEMORY
+void log_uninit(void);
+
+extern log_level log_min;
+
+// The basic structure that goes into the shared memory queue.
+// It is packed so the pid_t at the front is at the same location as
+// the one in log_crio_message.
+typedef struct log_message_t_ {
+ pid_t source;
+ log_level level;
+ char message[LOG_MESSAGE_LEN];
+ char name[40];
+ struct timespec time;
+ uint8_t sequence; // per process
+} __attribute__((packed)) log_message;
+
+#ifdef __cplusplus
+#define LOG_BOOL bool
+#else
+#define LOG_BOOL uint8_t
+#endif
+extern LOG_BOOL log_initted;
+#undef LOG_BOOL
+
+// Unless explicitly stated otherwise, format must always be a string constant
+// and args are printf-style arguments for format.
+// The validitiy of format and args together will be checked at compile time
+// using a gcc function attribute.
+
+// Logs the specified thing.
+#define LOG(level, format, args...) do { \
+ if (level >= log_min) { \
+ log_do(level, LOG_SOURCENAME ": " STRINGIFY(__LINE__) ": " format, ##args); \
+ } \
+} while (0)
+// Allows "bottling up" multiple log fragments which can then all be logged in
+// one message with LOG_UNCORK.
+// format does not have to be a constant
+#define LOG_CORK(format, args...) do { \
+ log_cork(__LINE__, format, ##args); \
+} while (0)
+// Actually logs all of the saved up log fragments (including format and args on
+// the end).
+#define LOG_UNCORK(level, format, args...) do { \
+ log_uncork(__LINE__, level, LOG_SOURCENAME ": %d-%d: ", format, ##args); \
+} while (0)
+// Makes a normal logging call if possible or just prints it out on stderr.
+#define LOG_IFINIT(level, format, args...) do{ \
+ if(log_initted) { \
+ LOG(level, format, args); \
+ } else { \
+ fprintf(stderr, "%s-noinit: " format, log_str(level), ##args); \
+ } \
+}while(0)
+
+// All functions return 0 for success and - for error.
+
+// Actually implements the basic logging call.
+// Does not check that level is valid.
+// TODO(brians): Fix this so it works with clang.
+int log_do(log_level level, const char *format, ...)
+ __attribute__((format(gnu_printf, 2, 3)));
+
+// TODO(brians): Fix this so it works with clang.
+int log_cork(int line, const char *format, ...)
+ __attribute__((format(gnu_printf, 2, 3)));
+// Implements the uncork logging call.
+// IMPORTANT: begin_format must have 2 %d formats as its only 2 format specifiers
+// which will get passed the minimum and maximum line numbers that have been
+// corked into this call.
+// TODO(brians): Fix this so it works with clang.
+int log_uncork(int line, log_level level, const char *begin_format,
+ const char *format, ...)
+ __attribute__((format(gnu_printf, 4, 5)));
+
+const log_message *log_read_next1(int flags);
+const log_message *log_read_next2(int flags, int *index);
+inline const log_message *log_read_next(void) { return log_read_next1(BLOCK); }
+void log_free_message(const log_message *msg);
+
+// The structure that is actually in the shared memory queue.
+union log_queue_message {
+ log_message atom;
+ log_crio_message crio;
+};
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
+