diff --git a/quad/.gitignore b/quad/.gitignore index 43d04fb118c3ab8c1ea06f84c8a8b11598990756..92bd47f407dc5d75d40fff7c329cb9ba87f3df11 100644 --- a/quad/.gitignore +++ b/quad/.gitignore @@ -5,3 +5,4 @@ lib/ lib-zybo/ TAGS out/ +bin/ \ No newline at end of file diff --git a/quad/Makefile b/quad/Makefile index 147ee25067ceb0bae3ffc9295e7a83a9bf37d00d..18875c630eee61348a964b38c0cdac57fc0d2eb5 100644 --- a/quad/Makefile +++ b/quad/Makefile @@ -1,13 +1,14 @@ INCDIR = inc LIBDIR = lib OUTDIR = out +EXEDIR = bin WS = $(CURDIR)/xsdk_workspace BOOT = $(OUTDIR)/BOOT.bin .PHONY: all libs zybo boot test clean deep-clean -all: libs +all: libs bins libs: $(MAKE) -C src/test @@ -16,6 +17,9 @@ libs: $(MAKE) -C src/commands $(MAKE) -C src/quad_app +bins: + $(MAKE) -C src/virt_quad + zybo: bash scripts/build_zybo.sh @@ -27,7 +31,7 @@ test: $(MAKE) -C src/quad_app test clean: - rm -rf $(INCDIR) $(LIBDIR) $(OUTDIR) + rm -rf $(INCDIR) $(LIBDIR) $(OUTDIR) $(EXEDIR) deep-clean: make clean diff --git a/quad/executable.mk b/quad/executable.mk new file mode 100644 index 0000000000000000000000000000000000000000..d17244a837c5c785fcf53ffb3f547d110d0be88a --- /dev/null +++ b/quad/executable.mk @@ -0,0 +1,43 @@ +GCC = gcc + +INCDIR = $(TOP)/inc +OBJDIR = obj +EXEDIR = $(TOP)/bin +LIBDIR = $(TOP)/lib + +SOURCES = $(wildcard *.c) +HEADERS = $(wildcard *.h) +INCLUDES = $(addprefix $(INCDIR)/, $(HEADERS)) +OBJECTS = $(patsubst %.c, $(OBJDIR)/%.o, $(SOURCES)) + +TARGET = $(EXEDIR)/$(NAME) + +.PHONY: default run clean + +################ +## User Targets +################ + +default: $(TARGET) + +run: $(TARGET) + $(EXEDIR)/$(NAME) + +clean: + rm -rf $(TARGET) $(OBJDIR) + +#################### +## Internal Targets +#################### + +$(TARGET): $(OBJECTS) | $(EXEDIR) + $(GCC) -g -o $(TARGET) $^ -I$(INCDIR) -L$(LIBDIR) $(REQLIBS) + +$(OBJDIR)/%.o : %.c | $(OBJDIR) $(INCDIR) + $(GCC) -c -g -o $@ $< -I$(INCDIR) + +$(OBJDIR): + mkdir $(OBJDIR) + +$(EXEDIR): + mkdir $(EXEDIR) diff --git a/quad/src/virt_quad/Makefile b/quad/src/virt_quad/Makefile new file mode 100644 index 0000000000000000000000000000000000000000..47cebc494626a024de63f93c15480f5e4c3ff5a4 --- /dev/null +++ b/quad/src/virt_quad/Makefile @@ -0,0 +1,6 @@ +TOP=../.. + +NAME = virt_quad +REQLIBS = -lquad_app -lcomputation_graph -lm -lcommands + +include $(TOP)/executable.mk diff --git a/quad/src/virt_quad/hw_impl_unix.c b/quad/src/virt_quad/hw_impl_unix.c new file mode 100644 index 0000000000000000000000000000000000000000..fea231c35e963f5321b35665e4c3c2feac961383 --- /dev/null +++ b/quad/src/virt_quad/hw_impl_unix.c @@ -0,0 +1,70 @@ +#include "hw_impl_unix.h" + +struct UARTDriver create_unix_uart() { + struct UARTDriver uart; + uart.state = NULL; + uart.reset = unix_uart_reset; + uart.write = unix_uart_write; + uart.read = unix_uart_read; + return uart; +} + +struct PWMOutputDriver create_unix_pwm_outputs() { + struct PWMOutputDriver pwm_outputs; + pwm_outputs.state = NULL; + pwm_outputs.reset = unix_pwm_output_reset; + pwm_outputs.write = unix_pwm_output_write; + return pwm_outputs; +} + +struct PWMInputDriver create_unix_pwm_inputs() { + struct PWMInputDriver pwm_inputs; + pwm_inputs.state = NULL; + pwm_inputs.reset = unix_pwm_input_reset; + pwm_inputs.read = unix_pwm_input_read; + return pwm_inputs; +} + +struct I2CDriver create_unix_i2c() { + struct I2CDriver i2c; + i2c.state = NULL; + i2c.reset = unix_i2c_reset; + i2c.write = unix_i2c_write; + i2c.read = unix_i2c_read; + return i2c; +} + +struct TimerDriver create_unix_global_timer() { + struct TimerDriver global_timer; + global_timer.state = NULL; + global_timer.reset = unix_global_timer_reset; + global_timer.restart = unix_global_timer_restart; + global_timer.read = unix_global_timer_read; + return global_timer; +} + +struct TimerDriver create_unix_axi_timer() { + struct TimerDriver axi_timer; + axi_timer.state = NULL; + axi_timer.reset = unix_axi_timer_reset; + axi_timer.restart = unix_axi_timer_restart; + axi_timer.read = unix_axi_timer_read; + return axi_timer; +} + +struct LEDDriver create_unix_mio7_led() { + struct LEDDriver mio7_led; + mio7_led.state = NULL; + mio7_led.reset = unix_mio7_led_reset; + mio7_led.turn_on = unix_mio7_led_turn_on; + mio7_led.turn_off = unix_mio7_led_turn_off; + return mio7_led; +} + +struct SystemDriver create_unix_system() { + struct SystemDriver sys; + sys.state = NULL; + sys.reset = unix_system_reset; + sys.sleep = unix_system_sleep; + return sys; +} diff --git a/quad/src/virt_quad/hw_impl_unix.h b/quad/src/virt_quad/hw_impl_unix.h new file mode 100644 index 0000000000000000000000000000000000000000..c7e3659dffcfb0b1094c26f41ffe3b4d792962b8 --- /dev/null +++ b/quad/src/virt_quad/hw_impl_unix.h @@ -0,0 +1,61 @@ +#ifndef HW_IMPL_UNIX +#define HW_IMPL_UNIX + +#include "hw_iface.h" +#include "type_def.h" + +#include <sys/time.h> +#include <stdio.h> +#include <unistd.h> +#include <stdlib.h> +#include <time.h> + +int unix_uart_reset(struct UARTDriver *self); +int unix_uart_write(struct UARTDriver *self, unsigned char c); +int unix_uart_read(struct UARTDriver *self, unsigned char *c); + +int unix_pwm_output_reset(struct PWMOutputDriver *self); +int unix_pwm_output_write(struct PWMOutputDriver *self, unsigned int channel, unsigned long pulse_width_us); + +int unix_pwm_input_reset(struct PWMInputDriver *self); +int unix_pwm_input_read(struct PWMInputDriver *self, unsigned int channel, unsigned long *pulse_width_us); + +int unix_i2c_reset(struct I2CDriver *self); +int unix_i2c_write(struct I2CDriver *self, + unsigned short device_addr, + unsigned char *data, + unsigned int length); +int unix_i2c_read(struct I2CDriver *self, + unsigned short device_addr, + unsigned char *buff, + unsigned int length); + +int unix_global_timer_reset(struct TimerDriver *self); +int unix_global_timer_restart(struct TimerDriver *self); +int unix_global_timer_read(struct TimerDriver *self, u64 *us); + +int unix_axi_timer_reset(struct TimerDriver *self); +int unix_axi_timer_restart(struct TimerDriver *self); +int unix_axi_timer_read(struct TimerDriver *self, u64 *us); + +int unix_mio7_led_reset(struct LEDDriver *self); +int unix_mio7_led_turn_on(struct LEDDriver *self); +int unix_mio7_led_turn_off(struct LEDDriver *self); + +int unix_system_reset(struct SystemDriver *self); +int unix_system_sleep(struct SystemDriver *self, unsigned long us); + +struct UARTDriver create_unix_uart(); +struct PWMOutputDriver create_unix_pwm_outputs(); +struct PWMInputDriver create_unix_pwm_inputs(); +struct I2CDriver create_unix_i2c(); +struct TimerDriver create_unix_global_timer(); +struct TimerDriver create_unix_axi_timer(); +struct LEDDriver create_unix_mio7_led(); +struct SystemDriver create_unix_system(); + +int test_unix_i2c(); +int test_unix_mio7_led_and_system(); +int test_unix_pwm_inputs(); + +#endif diff --git a/quad/src/virt_quad/hw_impl_unix_axi_timer.c b/quad/src/virt_quad/hw_impl_unix_axi_timer.c new file mode 100644 index 0000000000000000000000000000000000000000..73e9acc281110e6453bfba625976af852eeac351 --- /dev/null +++ b/quad/src/virt_quad/hw_impl_unix_axi_timer.c @@ -0,0 +1,24 @@ +#include "hw_impl_unix.h" + +int unix_axi_timer_reset(struct TimerDriver *self) { + if (self->state == NULL) { + self->state = malloc(sizeof(struct timeval)); + } + return 0; +} + +int unix_axi_timer_restart(struct TimerDriver *self) { + struct timeval *start = self->state; + struct timezone tz; + gettimeofday(start, &tz); + return 0; +} + +int unix_axi_timer_read(struct TimerDriver *self, u64 *us) { + struct timeval *start = self->state; + struct timeval end; + struct timezone tz; + gettimeofday(&end, &tz); + *us = end.tv_usec - start->tv_usec; + return 0; +} diff --git a/quad/src/virt_quad/hw_impl_unix_global_timer.c b/quad/src/virt_quad/hw_impl_unix_global_timer.c new file mode 100644 index 0000000000000000000000000000000000000000..be752b774eb55cb17f3c481947f44b76fc2ec124 --- /dev/null +++ b/quad/src/virt_quad/hw_impl_unix_global_timer.c @@ -0,0 +1,24 @@ +#include "hw_impl_unix.h" + +int unix_global_timer_reset(struct TimerDriver *self) { + if (self->state == NULL) { + self->state = malloc(sizeof(struct timeval)); + } + return 0; +} + +int unix_global_timer_restart(struct TimerDriver *self) { + struct timeval *start = self->state; + struct timezone tz; + gettimeofday(start, &tz); + return 0; +} + +int unix_global_timer_read(struct TimerDriver *self, u64 *us) { + struct timeval *start = self->state; + struct timeval end; + struct timezone tz; + gettimeofday(&end, &tz); + *us = end.tv_usec - start->tv_usec; + return 0; +} diff --git a/quad/src/virt_quad/hw_impl_unix_i2c.c b/quad/src/virt_quad/hw_impl_unix_i2c.c new file mode 100644 index 0000000000000000000000000000000000000000..09ab43c8b83b82d60dff7623a31efb1d29c3fd60 --- /dev/null +++ b/quad/src/virt_quad/hw_impl_unix_i2c.c @@ -0,0 +1,19 @@ +#include "hw_impl_unix.h" + +int unix_i2c_reset(struct I2CDriver *self) { + return 0; +} + +int unix_i2c_write(struct I2CDriver *self, + unsigned short device_addr, + unsigned char *data, + unsigned int length) { + return 0; +} + +int unix_i2c_read(struct I2CDriver *self, + unsigned short device_addr, + unsigned char *buff, + unsigned int length) { + return 0; +} diff --git a/quad/src/virt_quad/hw_impl_unix_mio7_led.c b/quad/src/virt_quad/hw_impl_unix_mio7_led.c new file mode 100644 index 0000000000000000000000000000000000000000..f96fda029e0c0a9664be8bd81e76a93af606e7ba --- /dev/null +++ b/quad/src/virt_quad/hw_impl_unix_mio7_led.c @@ -0,0 +1,23 @@ +#include "hw_impl_unix.h" + +int on; + +int unix_mio7_led_reset(struct LEDDriver *self) { + return 0; +} + +int unix_mio7_led_turn_on(struct LEDDriver *self) { + if (!on) { + puts("LED ON"); + on = 1; + } + return 0; +} + +int unix_mio7_led_turn_off(struct LEDDriver *self) { + if (on) { + puts("LED OFF"); + on = 0; + } + return 0; +} diff --git a/quad/src/virt_quad/hw_impl_unix_pwm_input.c b/quad/src/virt_quad/hw_impl_unix_pwm_input.c new file mode 100644 index 0000000000000000000000000000000000000000..8881f5f3815f063fb2ce365a6b07c79d7a2eaf44 --- /dev/null +++ b/quad/src/virt_quad/hw_impl_unix_pwm_input.c @@ -0,0 +1,50 @@ +#include "hw_impl_unix.h" + +int unix_pwm_input_reset(struct PWMInputDriver *self) { + return 0; +} + +int unix_pwm_input_read(struct PWMInputDriver *self, + unsigned int channel, + unsigned long *pulse_width_us) { + static int inc = 0; + unsigned long gear; + + switch (channel) { + case 0: + *pulse_width_us = 100000; + break; + case 1: + *pulse_width_us = 100000; + break; + case 2: + *pulse_width_us = 100000; + break; + case 3: + *pulse_width_us = 100000; + break; + case 4: + if (inc == 0) { + inc += 1; + puts("GEAR OFF"); + } + if (inc < 20) { + inc += 1; + gear = 120000; + } + else if (inc == 20) { + puts("GEAR ON"); + inc += 1; + } + else { + gear = 140000; + } + *pulse_width_us = gear; + break; + case 5: + // flap 1 + *pulse_width_us = 192000; + break; + } + return 0; +} diff --git a/quad/src/virt_quad/hw_impl_unix_pwm_output.c b/quad/src/virt_quad/hw_impl_unix_pwm_output.c new file mode 100644 index 0000000000000000000000000000000000000000..b549cd4367af0a5ebfe8a50cd7af97e94daf16bb --- /dev/null +++ b/quad/src/virt_quad/hw_impl_unix_pwm_output.c @@ -0,0 +1,12 @@ +#include "hw_impl_unix.h" + +int unix_pwm_output_reset(struct PWMOutputDriver *self) { + return 0; +} + +int unix_pwm_output_write(struct PWMOutputDriver *self, + unsigned int channel, + unsigned long pulse_width_us) { + //printf("PWM OUTPUT: %d %d\n", channel, pulse_width_us); + return 0; +} diff --git a/quad/src/virt_quad/hw_impl_unix_system.c b/quad/src/virt_quad/hw_impl_unix_system.c new file mode 100644 index 0000000000000000000000000000000000000000..27f1a691ee92f46f6be0e029245dfba51bfb9de0 --- /dev/null +++ b/quad/src/virt_quad/hw_impl_unix_system.c @@ -0,0 +1,14 @@ +#include "hw_impl_unix.h" + +int unix_system_reset(struct SystemDriver *sys) { + return 0; +} + +int unix_system_sleep(struct SystemDriver *sys, unsigned long us) { + struct timespec time; + struct timespec time2; + time.tv_sec = 0; + time.tv_nsec = us * 1000; + nanosleep(&time, &time2); + return 0; +} diff --git a/quad/src/virt_quad/hw_impl_unix_uart.c b/quad/src/virt_quad/hw_impl_unix_uart.c new file mode 100644 index 0000000000000000000000000000000000000000..f4787939832cd38d781643df1c9cd9d801f311b3 --- /dev/null +++ b/quad/src/virt_quad/hw_impl_unix_uart.c @@ -0,0 +1,13 @@ +#include "hw_impl_unix.h" + +int unix_uart_reset(struct UARTDriver *self) { + return 0; +} + +int unix_uart_write(struct UARTDriver *self, unsigned char c) { + return 0; +} + +int unix_uart_read(struct UARTDriver *self, unsigned char *c) { + return 0; +} diff --git a/quad/src/virt_quad/main.c b/quad/src/virt_quad/main.c new file mode 100644 index 0000000000000000000000000000000000000000..a87b8013f5037d6a2db5badd74c7166f681e3e8c --- /dev/null +++ b/quad/src/virt_quad/main.c @@ -0,0 +1,21 @@ +#include <stdio.h> +#include "hw_impl_unix.h" +#include "quad_app.h" + +int setup_hardware(hardware_t *hardware) { + hardware->i2c = create_unix_i2c(); + hardware->pwm_inputs = create_unix_pwm_inputs(); + hardware->pwm_outputs = create_unix_pwm_outputs(); + hardware->uart = create_unix_uart(); + hardware->global_timer = create_unix_global_timer(); + hardware->axi_timer = create_unix_axi_timer(); + hardware->mio7_led = create_unix_mio7_led(); + hardware->sys = create_unix_system(); + return 0; +} + +int main() +{ + quad_main(setup_hardware); + return 0; +}