<file_sep>/* Hello World Example

   This example code is in the Public Domain (or CC0 licensed, at your option.)

   Unless required by applicable law or agreed to in writing, this
   software is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
   CONDITIONS OF ANY KIND, either express or implied.
*/
#include <stdio.h>
#include "freertos/FreeRTOS.h"
#include "freertos/task.h"
#include "esp_system.h"
#include "esp_spi_flash.h"
#include <sodium.h>
#include <string.h>

#define PASSWORD "<PASSWORD>"

void app_main()
{
	// Bree: This is for troubleshooting / error-handling for libsodium (i.e. argon2)
	if (sodium_init() < 0)
	{
	printf("Sodium failed!\n");
	return;
	}

	char hashed_password[crypto_pwhash_STRBYTES];
	unsigned char salt[crypto_pwhash_SALTBYTES];
	unsigned char key[crypto_box_SEEDBYTES];
	randombytes_buf(salt, sizeof salt);
	
	// Bree: All print statements for error handling tests for argon2 functionality....
	// Bree: Remember!!!!
	//       In menuconfig: set MAIN TASK SIZE >= 8192 and set XTAL FREQ = 26 MHz
	
	if (crypto_pwhash_str(hashed_password, PASSWORD, strlen(PASSWORD), 3, 3) == -1) {
	printf("FAILED1!\n");
	}
	if (crypto_pwhash_str(hashed_password, PASSWORD, strlen(PASSWORD), 3, 10) == -1) {
	printf("FAILED2!\n");
	}
	if (crypto_pwhash_str(hashed_password, PASSWORD, strlen(PASSWORD), 3, 50) == -1) {
	printf("FAILED3!\n");
	}
	if (crypto_pwhash_str(hashed_password, PASSWORD, strlen(PASSWORD), 3, 150) == -1) {
	printf("FAILED4!\n");
	}
	if (crypto_pwhash_str(hashed_password, PASSWORD, strlen(PASSWORD), crypto_pwhash_OPSLIMIT_SENSITIVE, 512) == -1) {
	printf("FAILED5!\n");
	}
	if (crypto_pwhash_str(hashed_password, PASSWORD, strlen(PASSWORD), 3, 1024) == -1) {
	printf("FAILED6!\n");
	}
	if (crypto_pwhash_str(hashed_password, PASSWORD, strlen(PASSWORD), 3, 4096) == -1) {
	printf("FAILED7!\n");
	}
	if (crypto_pwhash_str(hashed_password, PASSWORD, strlen(PASSWORD), 3, 500000) == -1) {
	printf("FAILED8!\n");
	}
	if (crypto_pwhash_str(hashed_password, <PASSWORD>, strlen(PASSWORD), 3, crypto_pwhash_MEMLIMIT_INTERACTIVE) == -1) {
	printf("FAILED9!\n");
	}
	if (crypto_pwhash(key, sizeof key, PASSWORD, strlen(PASSWORD), salt, 3, 100, crypto_pwhash_ALG_DEFAULT) != 0)
	{
	printf("FAILED10!\n");
	}
	if (crypto_pwhash(key, sizeof key, PASSWORD, strlen(PASSWORD), salt, crypto_pwhash_OPSLIMIT_INTERACTIVE, crypto_pwhash_MEMLIMIT_INTERACTIVE, crypto_pwhash_ALG_DEFAULT) != 0)
	{
	printf("FAILED11!\n");
	}
//return;

// Bree: Here is the basic Hello World program (no more libsodium / argon2 error finding)
    printf("Hello world!\n");
    printf("\nWe are:\nBree\nDamon\nKouma\nSohin\n\n");
	
	
    /* Print chip information */
    esp_chip_info_t chip_info;
    esp_chip_info(&chip_info);
    printf("This is ESP32 chip with %d CPU cores, WiFi%s%s, ",
            chip_info.cores,
            (chip_info.features & CHIP_FEATURE_BT) ? "/BT" : "",
            (chip_info.features & CHIP_FEATURE_BLE) ? "/BLE" : "");

    printf("\nsilicon revision %d, ", chip_info.revision);

    printf("\n%dMB %s flash\n", spi_flash_get_chip_size() / (1024 * 1024),
            (chip_info.features & CHIP_FEATURE_EMB_FLASH) ? "embedded" : "external");

    for (int i = 10; i >= 0; i--) {
        printf("\nRestarting in %d seconds...\n", i);
        vTaskDelay(1000 / portTICK_PERIOD_MS);
    }
    printf("Restarting now.\n");
    fflush(stdout);
    esp_restart();
}
<file_sep>[X] Implement vTaskDelayUntil() to make the working sensors periodic.

[ ] Get dust sensor working

[ ] Get gas sensor working

[X] MQTT stuff

[ ] Output to LEDs from Manager

[ ] Write to OLED

[ ] Change Manager to require a password on startup

[ ] Check for USB input periodically in manager and have manager require a password then
	[ ] Check 5V(?) voltage via GPIO, it is apparently connected directly to the USB connection
	[ ] Implement user controls after password put in
	[ ] Check a flag to output read values to screen only after password input
	
[ ] Install a battery so code can continue after disconnection<file_sep>//Example static (known stack size) task creation:

	// Dimensions the buffer that the task being created will use as its stack.
	// NOTE:  This is the number of words the stack will hold, not the number of
	// bytes.  For example, if each stack item is 32-bits, and this is set to 100,
	// then 400 bytes (100 * 32-bits) will be allocated.
	#define STACK_SIZE 200

	// Structure that will hold the TCB of the task being created.
	StaticTask_t xTaskBuffer;

	// Buffer that the task being created will use as its stack.  Note this is
	// an array of StackType_t variables.  The size of StackType_t is dependent on
	// the RTOS port.
	StackType_t xStack[ STACK_SIZE ];

	// Function that implements the task being created.
	void vTaskCode( void * pvParameters )
	{
		// The parameter value is expected to be 1 as 1 is passed in the
		// pvParameters value in the call to xTaskCreateStatic().
		configASSERT( ( uint32_t ) pvParameters == 1UL );

		for( ;; )
		{
			// Task code goes here.
		}
	}

	// Function that creates a task.
	void vOtherFunction( void )
	{
		TaskHandle_t xHandle = NULL;

		// Create the task without using any dynamic memory allocation.
		xHandle = xTaskCreateStatic(
					  vTaskCode,       // Function that implements the task.
					  "NAME",          // Text name for the task.
					  STACK_SIZE,      // Stack size in words, not bytes.
					  ( void * ) 1,    // Parameter passed into the task.
					  tskIDLE_PRIORITY,// Priority at which the task is created.
					  xStack,          // Array to use as the task's stack.
					  &xTaskBuffer );  // Variable to hold the task's data structure.

		// puxStackBuffer and pxTaskBuffer were not NULL, so the task will have
		// been created, and xHandle will be the task's handle.  Use the handle
		// to suspend the task.
		
		vTaskSuspend( xHandle );
		//vTaskResume( xHandle ); to resume the task and it will run in accordance to its priority
		//INCLUDE_vTaskSuspend must be set to 1 otherwise can't supsend and resume tasks
		
		
	}
	
	

//relative delay for a task
void vTaskFunction( void * pvParameters )
{
// Block for 500ms.
const TickType_t xDelay = 500 / portTICK_PERIOD_MS;

    for( ;; )
    {
        // Simply toggle the LED every 500ms, blocking between each toggle.
        vToggleLED();
        vTaskDelay( xDelay );
    }
}


//takes taskhandle and gives the human-readable task name
char *pcTaskGetTaskName(TaskHandle_t xTaskToQuery)


//returns start of stack for xTask
uint8_t *pxTaskGetStackStart(TaskHandle_t xTask) //use NULL for xTask to return start stack of current task

<file_sep>#include <string.h>
#include <stdlib.h>

#include "sdkconfig.h"

#include "MQTTClient.h"

#include "freertos/FreeRTOS.h"
#include "freertos/task.h"
#include "freertos/event_groups.h"
#include "esp_wifi.h"
#include "esp_event_loop.h"
#include "esp_system.h"
#include "esp_task_wdt.h"
#include "esp_attr.h"
#include "nvs_flash.h"
#include "driver/gpio.h"
#include "driver/ledc.h"

#include "lwip/err.h"
#include "lwip/sockets.h"
#include "lwip/sys.h"
#include "lwip/netdb.h"
#include "lwip/dns.h"

#include "mbedtls/platform.h"
#include "mbedtls/net.h"
#include "mbedtls/debug.h"
#include "mbedtls/ssl.h"
#include "mbedtls/entropy.h"
#include "mbedtls/ctr_drbg.h"
#include "mbedtls/error.h"
#include "mbedtls/certs.h"

#include "fileTable.h"
#include "qExample.c"

/* The examples use simple WiFi configuration that you can set via
   'make menuconfig'.

   If you'd rather not, just change the below entries to strings with
   the config you want - ie #define EXAMPLE_WIFI_SSID "mywifissid"
 */

/* The event group allows multiple bits for each event,
   but we only care about one event - are we connected
   to the AP with an IP? */
const int CONNECTED_BIT = BIT0;

/* Constants that aren't configurable in menuconfig */
#define MQTT_SERVER "m15.cloudmqtt.com"
#define MQTT_USER "afhnaorh"
#define MQTT_PASS "<PASSWORD>"
#define MQTT_PORT 33521
#define MQTT_CLIENTID "GROUP2"
#define MQTT_WEBSOCKET 1  // 0=no 1=yes
#define MQTT_BUF_SIZE 512

xSemaphoreHandle print_mux;

static unsigned char mqtt_sendBuf[MQTT_BUF_SIZE];
static unsigned char mqtt_readBuf[MQTT_BUF_SIZE];

//static unsigned char mqtt_sendBuf[MQTT_BUF_SIZE];
//static unsigned char mqtt_readBuf[MQTT_BUF_SIZE];

static const char *CTAG = "MQTTS";





/* FreeRTOS event group to signal when we are connected & ready to make a request */
EventGroupHandle_t wifi_event_group;

static esp_err_t event_handler(void *ctx, system_event_t *event)
{
    switch(event->event_id) {
        case SYSTEM_EVENT_STA_START:
            esp_wifi_connect();
            break;
        case SYSTEM_EVENT_STA_GOT_IP:
            xEventGroupSetBits(wifi_event_group, CONNECTED_BIT);
            break;
        case SYSTEM_EVENT_STA_DISCONNECTED:
            /* This is a workaround as ESP32 WiFi libs don't currently
               auto-reassociate. */
            esp_wifi_connect();
            xEventGroupClearBits(wifi_event_group, CONNECTED_BIT);
            break;
        default:
            break;
    }
    return ESP_OK;
}

void mqtt_task(void *pvParameters)
{
	int ret;
	//define values used in vTaskDelayUntil() to make task periodic
		TickType_t xLastWakeTime;
		//portTICK_RATE_MS converts from ms to ticks, allowing me to say
		//"10000 milliseconds" and not care about my board's tick rate
		const TickType_t xFrequency = 5000*portTICK_RATE_MS;
	while(1){
			xLastWakeTime = xTaskGetTickCount();
			Network network;
			MQTTClient client;
			NetworkInit(&network);
			network.websocket = MQTT_WEBSOCKET;
			
			
			xEventGroupWaitBits(wifi_event_group, CONNECTED_BIT, false, true, portMAX_DELAY);
			
			ret = NetworkConnect(&network, MQTT_SERVER, MQTT_PORT);
			
			MQTTClientInit(&client, &network,
            2000,            // command_timeout_ms
            mqtt_sendBuf,         //sendbuf,
            MQTT_BUF_SIZE, //sendbuf_size,
            mqtt_readBuf,         //readbuf,
            MQTT_BUF_SIZE  //readbuf_size
            );

		char buf[30];
		MQTTString clientId = MQTTString_initializer;
		sprintf(buf, MQTT_CLIENTID);
		clientId.cstring = buf;

		MQTTString username = MQTTString_initializer;
		username.cstring = MQTT_USER;	
		
		MQTTString password = MQTTString_initializer;
		password.cstring = MQTT_PASS;
		
		MQTTPacket_connectData data = MQTTPacket_connectData_initializer;
		data.clientID          = clientId;
		data.willFlag          = 0;
		data.MQTTVersion       = 4; // 3 = 3.1 4 = 3.1.1
		data.keepAliveInterval = 5;
		data.cleansession      = 1;
		data.username          = username;
		data.password          = <PASSWORD>;
		
		ret = MQTTConnect(&client, &data);
		if (ret != SUCCESS) {
        printf("\n\nError I think: %d\n\n",ret);
		goto exit;
		}
		printf("\n\nError I thinkn't: %d\n\n",ret);		
		
		
		char msgbuf[200];
		MQTTMessage message;
		message.qos = QOS0;
        message.retained = false;
        message.dup = false;
        message.payload = (void*)msgbuf;
        message.payloadlen = strlen(msgbuf)+1;
		
		toComm = popW();	
		

	switch(toComm%10){
		case 0:
			//publish to iupui/group2/temperature
			printf("\n\nPublish to temp\n\n");
			sprintf(msgbuf, "{\"temperature\":%d,}", toComm);
			printf("\n\n%s\n\n",msgbuf);	
			ret = MQTTPublish(&client, "iupui/group2/", &message);
			//toComm = -1234;
			if (ret != SUCCESS) {
					printf("MQTTPublish NOT: %d", ret);
			}else{
				printf("MQTTPublish wait I think it did: %d",ret);
			}	
		 
			break;
		case 1:
			//publish to iupui/group2/humidity
			printf("\n\nPublish to humidity\n\n");
			sprintf(msgbuf, "{\"humidity\":%d,}", toComm);
			printf("\n\n%s\n\n",msgbuf);	
			ret = MQTTPublish(&client, "iupui/group2/", &message);
			toComm = -1234;
			if (ret != SUCCESS) {
				printf("MQTTPublish NOT: %d", ret);
			}else{
				printf("MQTTPublish wait I think it did: %d",ret);
			}	
			
			break;
		case 2: 
			//publish to iupui/group2/light
			printf("\n\nPublish to light\n\n");
			
			sprintf(msgbuf, "{\"light\":%d,}", toComm);
			printf("\n\n%s\n\n",msgbuf);	
			ret = MQTTPublish(&client, "iupui/group2/", &message);
			toComm = -1234;
			if (ret != SUCCESS) {
				printf("MQTTPublish NOT: %d", ret);
			}else{
				printf("MQTTPublish wait I think it did: %d",ret);
			}	
			
			break;
		default:
			//no publish
			printf("\n\n | COMM TASK ERROR | Out-of-bounds value put into toComm\n\n");
			break;

			}//end switch case
		
			
			

		
			
			//printf("\n\n| COMM TASK | Before delay\n\n");
			vTaskDelayUntil(&xLastWakeTime, xFrequency);
			//printf("\n\n| COMM TASK | After delay\n\n");
	
exit:
    MQTTDisconnect(&client);
    NetworkDisconnect(&network);
	}
}


static void initialise_wifi(void)
{
    tcpip_adapter_init();
    wifi_event_group = xEventGroupCreate();
    ESP_ERROR_CHECK( esp_event_loop_init(event_handler, NULL) );
    wifi_init_config_t cfg = WIFI_INIT_CONFIG_DEFAULT();
    ESP_ERROR_CHECK( esp_wifi_init(&cfg) );
    ESP_ERROR_CHECK( esp_wifi_set_storage(WIFI_STORAGE_RAM) );
    wifi_config_t wifi_config = {
        .sta = {
            .ssid = "AndroidAP",
            .password = "<PASSWORD>",
        },
    };
    ESP_LOGI(CTAG, "Setting WiFi configuration SSID %s...", wifi_config.sta.ssid);
    ESP_ERROR_CHECK( esp_wifi_set_mode(WIFI_MODE_STA) );
    ESP_ERROR_CHECK( esp_wifi_set_config(ESP_IF_WIFI_STA, &wifi_config) );
    ESP_ERROR_CHECK( esp_wifi_start() );
}


void comms_open()
{
    nvs_flash_init();
    initialise_wifi();

    // MQTT and TLS needs a deep stack, 12288 seems to work, anything
    // less will get us a stack overflow error
    xTaskCreate(&mqtt_task, "mqtt_task", 12288, NULL, 5, NULL);

}
<file_sep>/*
 * MIT License
 *
 * Copyright (c) 2017 <NAME>
 *
 * Permission is hereby granted, free of charge, to any person obtaining a copy
 * of this software and associated documentation files (the "Software"), to deal
 * in the Software without restriction, including without limitation the rights
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 * copies of the Software, and to permit persons to whom the Software is
 * furnished to do so, subject to the following conditions:
 *
 * The above copyright notice and this permission notice shall be included in all
 * copies or substantial portions of the Software.
 *
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
 * SOFTWARE.
 */

/**
 * @file tsl2561.h
 * @brief Interface definitions for the ESP32-compatible TSL2561 Light to Digital Converter component.
 *
 * This component provides structures and functions that are useful for communicating with the device.
 *
 * Technically, the TSL2561 device is an I2C not SMBus device, however the datasheet makes it clear
 * that most SMBus operations are compatible with this device, so it makes sense to use an SMBus interface
 * to manage communication.
 */

#ifndef TSL2561_H
#define TSL2561_H

#include <stdbool.h>
#include "../../esp32-smbus/include/smbus.h"

#ifdef __cplusplus
extern "C" {
#endif

/**
 * @brief Enum for recognised TSL256x devices
 */
typedef enum
{
    TSL2561_DEVICE_TYPE_INVALID = 0b1111,         ///< Invalid device
    TSL2561_DEVICE_TYPE_TSL2560CS = 0b0000,       ///< TSL2560CS (Chipscale)
    TSL2561_DEVICE_TYPE_TSL2561CS = 0b0001,       ///< TSL2561CS (Chipscale)
    TSL2561_DEVICE_TYPE_TSL2560T_FN_CL = 0b0100,  ///< TSL2560T/FN/CL (TMB-6 or Dual Flat No-Lead-6 or ChipLED-6)
    TSL2561_DEVICE_TYPE_TSL2561T_FN_CL = 0b0101,  ///< TSL2561T/FN/CL (TMB-6 or Dual Flat No-Lead-6 or ChipLED-6)
} tsl2561_device_type_t;

/**
 * @brief Enum for supported integration durations.
 * These durations assume the default internal oscillator frequency of 735 kHz.
 */
typedef enum
{
    TSL2561_INTEGRATION_TIME_13MS = 0x00,   ///< Integrate over 13.7 milliseconds
    TSL2561_INTEGRATION_TIME_101MS = 0x01,  ///< Integrate over 101 milliseconds
    TSL2561_INTEGRATION_TIME_402MS = 0x02,  ///< Integrate over 402 milliseconds
} tsl2561_integration_time_t;

/**
 * @brief Enum for supported gain values.
 */
typedef enum
{
    TSL2561_GAIN_1X = 0x00,
    TSL2561_GAIN_16X = 0x10,
} tsl2561_gain_t;

typedef uint8_t tsl2561_revision_t;    ///< The type of the IC's revision value
typedef uint16_t tsl2561_visible_t;    ///< The type of a visible light measurement value
typedef uint16_t tsl2561_infrared_t;   ///< The type of an infrared light measurement value

/**
 * @brief Structure containing information related to the SMBus protocol.
 */
typedef struct
{
    bool init;                                    ///< True if struct has been initialised, otherwise false
    bool powered;                                 ///< True if the device has been powered up
    smbus_info_t * smbus_info;                    ///< Pointer to associated SMBus info
    tsl2561_device_type_t device_type;            ///< Detected type of device (Chipscale vs T/FN/CL)
    tsl2561_integration_time_t integration_time;  ///< Current integration time for measurements
    tsl2561_gain_t gain;                          ///< Current gain for measurements
} tsl2561_info_t;

/**
 * @brief Construct a new TSL2561 info instance.
 *        New instance should be initialised before calling other functions.
 * @return Pointer to new device info instance, or NULL if it cannot be created.
 */
tsl2561_info_t * tsl2561_malloc(void);

/**
 * @brief Delete an existing TSL2561 info instance.
 * @param[in,out] tsl2561_info Pointer to TSL2561 info instance that will be freed and set to NULL.
 */
void tsl2561_free(tsl2561_info_t ** tsl2561_info);

/**
 * @brief Initialise a TSL2561 info instance with the specified SMBus information.
 * @param[in] tsl2561_info Pointer to TSL2561 info instance.
 * @param[in] smbus_info Pointer to SMBus info instance.
 */
esp_err_t tsl2561_init(tsl2561_info_t * tsl2561_info, smbus_info_t * smbus_info);

/**
 * @brief Retrieve the Device Type ID and Revision number from the device.
 * @param[in] tsl2561_info Pointer to initialised TSL2561 info instance.
 * @param[out] device The retrieved Device Type ID.
 * @param[out] revision The retrieved Device Revision number.
 * @return ESP_OK if successful, ESP_FAIL or ESP_ERR_* if an error occurred.
 */
esp_err_t tsl2561_device_id(const tsl2561_info_t * tsl2561_info, tsl2561_device_type_t * device, tsl2561_revision_t * revision);

/**
 * @brief Set the integration time and gain. These values are set together
 *        as they are programmed via the same register.
 * @param[in] tsl2561_info Pointer to initialised TSL2561 info instance.
 * @param[out] integration_time The integration time to use for the next measurement.
 * @param[out] infrared The gain setting to use for the next measurement.
 * @return ESP_OK if successful, ESP_FAIL or ESP_ERR_* if an error occurred.
 */
esp_err_t tsl2561_set_integration_time_and_gain(tsl2561_info_t * tsl2561_info, tsl2561_integration_time_t integration_time, tsl2561_gain_t gain);

/**
 * @brief Retrieve a visible and infrared light measurement from the device.
 *        This function will sleep until the integration time has passed.
 * @param[in] tsl2561_info Pointer to initialised TSL2561 info instance.
 * @param[out] visible The resultant visible light measurement.
 * @param[out] infrared The resultant infrared light measurement.
 * @return ESP_OK if successful, ESP_FAIL or ESP_ERR_* if an error occurred.
 */
esp_err_t tsl2561_read(tsl2561_info_t * tsl2561_info, tsl2561_visible_t * visible, tsl2561_infrared_t * infrared);

/**
 * @brief Compute the Lux approximation from a visible and infrared light measurement.
 *        The calculation is performed according to the procedure given in the datasheet.
 * @param[in] tsl2561_info Pointer to initialised TSL2561 info instance.
 * @param[in] visible The visible light measurement.
 * @param[in] infrared The infrared light measurement.
 * @return The resulting approximation of the light measurement in Lux.
 */
uint32_t tsl2561_compute_lux(const tsl2561_info_t * tsl2561_info, tsl2561_visible_t visible, tsl2561_infrared_t infrared);

#ifdef __cplusplus
}
#endif

#endif  // TSL2561_H
<file_sep>/*
ECE-566 RTOS - FALL 2018
Adapted by <NAME>

For: DHT22 Temp & Humidity Sensor + LED  

*/

#include <stdio.h>
#include "freertos/FreeRTOS.h"
#include "freertos/task.h"
#include "esp_system.h"
#include "rom/ets_sys.h"
#include "nvs_flash.h"
#include "driver/gpio.h"
#include "sdkconfig.h"

#include "DHT22.h"
#include "qExample.c"
#include "fileTable.h"

#ifndef DHT_MAIN
#define DHT_MAIN

//#define BLINK_GPIO CONFIG_BLINK_GPIO  // Bree: These are for setting via menuconfig but we don't need

//Damon: Create a task handle that's very visible to allow sensor.c to view it in the most unsafe manner possible
TaskHandle_t handleDHT = NULL;
TaskHandle_t handleHumid = NULL;



int temp_read();
int humid_read();

int tempValue = 0; //read updates these values, write puts them onto the queue
int humidValue = 0;

float SSt = 0; //to find the standard deviation of temperature task, take sum of values and sum of squared values, then divide by n
float St = 0;
int nt = 0;

float SSh = 0;
float Sh = 0;
int nh = 0;

int TEMP_TASK_PERIOD = 10000;
int HUMID_TASK_PERIOD = 10000; 

// Bree: define DHT22 task function
void temp_task(void *pvParameter)
{
		//define values used in vTaskDelayUntil() to make task periodic
		TickType_t xLastWakeTime;
		TickType_t x2DoneWithTask;
		const TickType_t xFrequency = TEMP_TASK_PERIOD*portTICK_RATE_MS;

	while(1){
		xLastWakeTime = xTaskGetTickCount();

		temp_read(); //temp_task periodically updates the value
		
		//For dev use only. Used in determining task characteristics
		x2DoneWithTask = xTaskGetTickCount();
		
		
		St += x2DoneWithTask - xLastWakeTime;
		SSt += (x2DoneWithTask - xLastWakeTime)*(x2DoneWithTask - xLastWakeTime);
		nt++;
		
		printf("\n\nTemp Task Info: %d Ticks to complete task",(x2DoneWithTask - xLastWakeTime));
		printf("\nTemp Task Info: %f is Standard Deviation", ((SSt/nt) - (St/nt)*(St/nt))); //this is 0 because DHT22 takes 3 ticks to read by design
		printf("\nTemp Task Info: %d is Temperature Slack Time", 100 - (x2DoneWithTask - xLastWakeTime));
		printf("\nTemp Task Info: %d is utilization", (x2DoneWithTask - xLastWakeTime)/TEMP_TASK_PERIOD);
		printf("\nTemp Task Info: %d is Task Period", TEMP_TASK_PERIOD);
		 //
		
		vTaskDelayUntil(&xLastWakeTime, xFrequency);
		
	
	}

}

void humid_task(void *pvParameter)
{
	//see temp_task for explanation of periodic task control
	TickType_t hLastWakeTime;
	TickType_t h2DoneWithTask;
	const TickType_t hFrequency = 10000*portTICK_RATE_MS;
	while(1){
		hLastWakeTime = xTaskGetTickCount();
		humid_read(); //temp_task periodically updates the value
		
		//For dev use only. Used in determining task characteristics
		h2DoneWithTask = xTaskGetTickCount();
		
		
		Sh += h2DoneWithTask - hLastWakeTime;
		SSh += (h2DoneWithTask - hLastWakeTime)*(h2DoneWithTask - hLastWakeTime);
		nh++;
		
		printf("\n\nTemp Task Info: %d Ticks to complete task",(h2DoneWithTask - hLastWakeTime));
		printf("\nTemp Task Info: %f is Standard Deviation", ((SSh/nh) - (Sh/nh)*(Sh/nh))); //this is 0 because DHT22 takes 3 ticks to read by design
		printf("\nTemp Task Info: %d is Temperature Slack Time", 100 - (h2DoneWithTask - hLastWakeTime));
		printf("\nTemp Task Info: %d is utilization", (h2DoneWithTask - hLastWakeTime)/HUMID_TASK_PERIOD);
		printf("\nTemp Task Info: %d is Task Period", HUMID_TASK_PERIOD);
		 //
		
		vTaskDelayUntil(&hLastWakeTime, hFrequency);
		

	}
}

//Bree: define LED Blink task function
void blink_task(void *pvParameter)
{
    /* Configure the IOMUX register for pad BLINK_GPIO (some pads are
       muxed to GPIO on reset already, but some default to other
       functions and need to be switched to GPIO. Consult the
       Technical Reference for a list of pads and their default
       functions.)
    */
    //gpio_pad_select_gpio(LEDgpio);
	setLEDgpio( 2 );
    /* Set the GPIO as a push/pull output */
    gpio_set_direction(2, GPIO_MODE_OUTPUT);
    while(1) {
        /* Blink off (output low) */
        gpio_set_level(2, 0);
        vTaskDelay(1000 / portTICK_PERIOD_MS);
        /* Blink on (output high) */
        gpio_set_level(2, 1);
        vTaskDelay(1000 / portTICK_PERIOD_MS);
    }
}

int temp_read(){
	setDHTgpio( 23 );    // Bree: 23 is what I chose to set my default gpio for DHT
	
		int ret = readDHT();
		
		errorHandler(ret);
		
		tempValue = getTemperature();
		return getTemperature();
}

void temp_ioctl(int input){ //change values of temp
	TEMP_TASK_PERIOD = input;
}

int temp_write(){
	int ret = tempValue;
	ret = ret*10; //the "name" for temperature is put into the ones' place, so value needs to be multiplied by 10 to make room
	ret = ret+0; //name for temperature is 0
	pushQ(&ret);
	return ret;
}

void humid_ioctl(int input){
	HUMID_TASK_PERIOD = input;
}

void humid_close(){
	vTaskSuspend(handleHumid);
}

void temp_close(){
	vTaskSuspend(handleDHT);
}

void temp_open()
{
	if(handleDHT == NULL){	//on first call, define this task
	// DHT22 Read task code (from original DHT22 program)
	nvs_flash_init();
	vTaskDelay( 1000 / portTICK_RATE_MS );
	xTaskCreate( &temp_task, "TempTask", 2048, NULL, 5, &handleDHT );
	struct row tempRow;
	tempRow.read = temp_read;
	tempRow.name = 1;
	tempRow.write = temp_write;
	tempRow.close = temp_close;
	tempRow.open = temp_open;
	devTable[rowsInUse++] = tempRow;
	}else{ //on every other call, resume this task
		vTaskResume(handleDHT);
	}
	// LED Blink task code (from original LED Blink program)
	//xTaskCreate(&blink_task, "blink_task", configMINIMAL_STACK_SIZE, NULL, 5, NULL);
}

int humid_read(){
	setDHTgpio( 23 );    // Bree: 23 is what I chose to set my default gpio for DHT
		
		int ret = readDHT();
		errorHandler(ret);
		
		//printf("\n| Humid_Read | Humidity Task has this name: %d",devTable[1].name);
		return getHumidity();
}

int humid_write(){

     	// Initialise the xLastWakeTime variable with the current time.
	
     	int ret = (int)getHumidity();
	ret = ret*10; //the "name" for humidity is put into the ones place of the read value
	ret += 1; //humidity = 1
	pushQ(&ret); //puts humidity value onto queue
	return ret;
}

void humid_open()
{
	if(handleHumid == NULL){ //on first call, define this task
	// DHT22 Read task code (from original DHT22 program)
	nvs_flash_init();
	vTaskDelay( 1000 / portTICK_RATE_MS );
	//Damon: These task definitions mean it only looks at humidity side of things
	xTaskCreate( &humid_task, "HumidTask", 2048, NULL, 5, &handleHumid );
	struct row humidRow;
	humidRow.read = humid_read;
	humidRow.write = humid_write;
	humidRow.open = humid_open;
	humidRow.close = humid_close;
	humidRow.name = 2;
	devTable[rowsInUse++] = humidRow;
	}else{ //on every other call, resume this task
		vTaskResume(handleHumid);
		
	}
}
#endif
<file_sep>/*	queues.c 	*/

#include <stdio.h>

#include "freertos/FreeRTOS.h"

#include "freertos/task.h"

#include "freertos/queue.h"

#ifndef QUEUE_MAIN
#define QUEUE_MAIN



QueueHandle_t  q=NULL;
QueueHandle_t  w=NULL;
/*
void consumer_task(void *pvParameter)

{

    unsigned long counter;

    if(q == NULL){

        printf("Queue is not ready");

        return;

    }

    while(1){

        xQueueReceive(q,&counter,(TickType_t )(1000/portTICK_PERIOD_MS)); 

        printf("value received on queue: %lu \n",counter);

        vTaskDelay(500/portTICK_PERIOD_MS); //wait for 500 ms

    }

}
*/

/*
void producer_task(void *pvParameter){

    unsigned long counter=1;

    if(q == NULL){

        printf("Queue is not ready \n");

        return;

    }

    while(1){

         printf("value sent on queue: %lu \n",counter);

         xQueueSend(q,(void *)&counter,(TickType_t )0); // add the counter value to the queue

         counter++;

         vTaskDelay(1000/portTICK_PERIOD_MS); //wait for a second

    }

}
*/

void pushQ(int* input){
	xQueueSend(q,input,(TickType_t)0);
	//printf("\nValue sent to queue: %d\n",*input);
	vTaskDelay(1000/portTICK_PERIOD_MS);
}

int popQ(){
	unsigned long storage;
	xQueueReceive(q,&storage,(TickType_t )(1000/portTICK_PERIOD_MS));
	//printf("\nValue read off queue: %lu \n",storage);
	return (int)storage;
}

int popW(){ //w holds the values manager wants communicated
	unsigned long storage;
	xQueueReceive(w,&storage,(TickType_t )(1000/portTICK_PERIOD_MS));
	//printf("\nValue read off queue: %lu \n",storage);
	return (int)storage;
}

void pushW(int* input){
	xQueueSend(w,input,(TickType_t)0);
	//printf("\nValue sent to queue: %d\n",*input);
	vTaskDelay(1000/portTICK_PERIOD_MS);
}

void q_app_main()

{	

    q=xQueueCreate(20,sizeof(unsigned long));

    w=xQueueCreate(20,sizeof(unsigned long));

    if(q != NULL && w != NULL){

        printf("Queues are created\n");

        vTaskDelay(1000/portTICK_PERIOD_MS); //wait for a second

        //xTaskCreate(&producer_task,"producer_task",2048,NULL,5,NULL);

        //printf("producer task  started\n");

        //xTaskCreate(&consumer_task,"consumer_task",2048,NULL,5,NULL);

        //printf("consumer task  started\n");

    }else{

        printf("Queue creation failed");

    }    

}
#endif
<file_sep>#ifndef FILETABLE_SEEN
#define FILETABLE_SEEN

struct row{

	int name;
	int (*read)();
	int (*write)();
	void (*close)();
	void (*open)();
};
int rowsInUse = 0;
struct row devTable[6];
int toComm = -1234; //the data being sent to comm
int signature[6] = {0,0,0,0,0,0}; //devTable[i] has its signature put into signature[i]. Values in signature[] range from -2 to +2 to represent VERY LOW, LOW, NORMAL, HIGH, and VERY HIGH, respectively.

int passFlag = 0; //check if password has been implemented. If not, don't print anything to screen

#endif //FILETABLE_SEEN
<file_sep>#include <stdio.h>
#include "fileTable.h"
#include "DHT_main.c"

TaskHandle_t handleCommand = NULL;
gpio_num_t FIRE_ALARM_GPIO = GPIO_NUM_14; //variables to make them easier to change
gpio_num_t FURNACE_GPIO = GPIO_NUM_15;
gpio_num_t AC_GPIO = GPIO_NUM_16;
gpio_num_t HUMIDIFIER_GPIO = GPIO_NUM_17;
gpio_num_t GAS_LEAK_GPIO = GPIO_NUM_18;

void command_task(void* pvParameter){ //go through the signature array to see if any values or combination of values are dangerous, then set various LEDs to represent system responses

    TickType_t CommandLastWakeTime;
    const TickType_t CommandFrequency = 2000*portTICK_RATE_MS; //period of two seconds because things like fire and the need to turn on AC are important
	
	while(1){ //task goes through signature[] and sets output values based on dangerous scenarios
		
		CommandLastWakeTime = xTaskGetTickCount();
		
		if(signature[0] == 2 && signature[4] == 2){ //heat and particle sensors both going nuts
				gpio_set_level(FIRE_ALARM_GPIO, 1);
				
				if(passFlag == 1){ printf("\n\nFIRE!\n\n"); }
			
			}else
				gpio_set_level(FIRE_ALARM_GPIO, 0);
		
		if(signature[0] < 0 && signature[2] > -1){ //if lights are on (i.e., employees in the building) and temperature is below 20C, power furnace
				gpio_set_level(FURNACE_GPIO, 1);
				
				if(passFlag == 1){ printf("\n\nTurning on furnace %d\n\n", passFlag); }
		}else
			gpio_set_level(FURNACE_GPIO, 0);
		
		if(signature[0] > 0 && signature[2] > -1){ //if lights are on and temperature is above 25C, power AC
				gpio_set_level(AC_GPIO, 1);

				if(passFlag == 1){ printf("\n\nTurning on air conditioning\n\n"); }
		}else
			gpio_set_level(AC_GPIO, 1);
		
		if(signature[1] > 0 && signature[2] > -1){ //if lights are on and humidity is up, use dehumidifier
				gpio_set_level(HUMIDIFIER_GPIO, 1);
			
				if(passFlag == 1){ printf("\n\nTurning on dehumidifier"); }
		}else
				gpio_set_level(HUMIDIFIER_GPIO, 0);
		
		if(signature[3] > 0){ //if gas leak detected, raise an alarm regardless of the time of day
				gpio_set_level(GAS_LEAK_GPIO, 1);

				if(passFlag == 1) {printf("\n\nPOSSIBLE GAS LEAK\n\n"); }
		}else
			gpio_set_level(GAS_LEAK_GPIO, 0);
		
		
		
		
		vTaskDelayUntil(&CommandLastWakeTime, CommandFrequency);

		
	}
	
}

void command_open(){
	xTaskCreate(&command_task, "command_task", 1024, NULL, 5, handleCommand);
	
}
<file_sep>/********************************************************************************************************
	By:				<NAME>
	For:			TSL2561 Light-to-Digital sensor, for use with ESP32 with ESP-IDF
	
	Adapted from:	David Antliff
					( see https://github.com/DavidAntliff/esp32-tsl2561-example.git )
					
					
//  BREE NOTES:		I ran ESP32's I2C example prgrogram first to configure / choose 
					which of ESP32's GPIO pins to set as SDA (data) master and SCL (clock) master.
					For my board, the best choice was GPIO 18 (SDA) ad GPIO 19(SCL) but your
					board may very well be different so check the pinout in your datasheet!
					
					Also, it's important to understand the I2C is a Master-Slave connection,
					and you must wire your Master SDA and SCL pins to your Slave SDA and SCL
					pins, respectively. Finally, you also connect the sensor's SDA and SCL pins 
					to the Master SDA and SCL pins.
					
					Be sure to only connect the sensor's VCC to 3.3V! 5V will damage it.
//
//
 * MIT License
 *
 * Copyright (c) 2017 <NAME>
 *
 * Permission is hereby granted, free of charge, to any person obtaining a copy
 * of this software and associated documentation files (the "Software"), to deal
 * in the Software without restriction, including without limitation the rights
 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
 * copies of the Software, and to permit persons to whom the Software is
 * furnished to do so, subject to the following conditions:
 *
 * The above copyright notice and this permission notice shall be included in all
 * copies or substantial portions of the Software.
 *
 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
 * SOFTWARE.
 */

/**
 * @file app_main.c
 * @brief Example application for the TSL2561 Light-to-Digital Converter.
 */

#include <stdio.h>
#include "freertos/FreeRTOS.h"
#include "freertos/task.h"
#include "esp_system.h"
#include "driver/gpio.h"
#include "driver/i2c.h"
#include "esp_log.h"
#include "sdkconfig.h"

#include "../components/esp32-smbus/include/smbus.h"
#include "../components/esp32-tsl2561/include/tsl2561.h"
#include "qExample.c"
#include "fileTable.h"

#ifndef LIGHT_MAIN
#define LIGHT_MAIN

#define TAG *"app"

#define I2C_MASTER_NUM           I2C_NUM_0
#define I2C_MASTER_TX_BUF_LEN    0                     // disabled
#define I2C_MASTER_RX_BUF_LEN    0                     // disabled
#define I2C_MASTER_FREQ_HZ       100000
#define I2C_MASTER_SDA_IO        CONFIG_I2C_MASTER_SDA
#define I2C_MASTER_SCL_IO        CONFIG_I2C_MASTER_SCL



void tsl2561_output();
int lightValueRead = 0;

TaskHandle_t handleLight = NULL;

static void i2c_master_init(void)
{
    int i2c_master_port = I2C_MASTER_NUM;
    i2c_config_t conf;
    conf.mode = I2C_MODE_MASTER;
    conf.sda_io_num = I2C_MASTER_SDA_IO;
    conf.sda_pullup_en = GPIO_PULLUP_DISABLE;  // GY-2561 provides 10kΩ pullups
    conf.scl_io_num = I2C_MASTER_SCL_IO;
    conf.scl_pullup_en = GPIO_PULLUP_DISABLE;  // GY-2561 provides 10kΩ pullups
    conf.master.clk_speed = I2C_MASTER_FREQ_HZ;
    i2c_param_config(i2c_master_port, &conf);
    i2c_driver_install(i2c_master_port, conf.mode,
                       I2C_MASTER_RX_BUF_LEN,
                       I2C_MASTER_TX_BUF_LEN, 0);
}

int light_read(){
	return lightValueRead;
}

void tsl2561_task(void * pvParameter)
{
    //Every 10 seconds, update the read value
    TickType_t lLastWakeTime;
    const TickType_t lFrequency = 10000*portTICK_RATE_MS;


    // Set up I2C
    i2c_master_init();
    i2c_port_t i2c_num = I2C_MASTER_NUM;
    uint8_t address = CONFIG_TSL2561_I2C_ADDRESS;

    // Set up the SMBus
    smbus_info_t * smbus_info = smbus_malloc();
    smbus_init(smbus_info, i2c_num, address);
    smbus_set_timeout(smbus_info, 1000 / portTICK_RATE_MS);

    // Set up the TSL2561 device
    tsl2561_info_t * tsl2561_info = tsl2561_malloc();
    tsl2561_init(tsl2561_info, smbus_info);

    // Set sensor integration time and gain
    tsl2561_set_integration_time_and_gain(tsl2561_info, TSL2561_INTEGRATION_TIME_402MS, TSL2561_GAIN_1X);
    //tsl2561_set_integration_time_and_gain(tsl2561_info, TSL2561_INTEGRATION_TIME_402MS, TSL2561_GAIN_16X);

    while (1)
    {
	lLastWakeTime = xTaskGetTickCount();

        tsl2561_visible_t visible = 0;
        tsl2561_infrared_t infrared = 0;
        tsl2561_read(tsl2561_info, &visible, &infrared);
	lightValueRead = tsl2561_compute_lux(tsl2561_info, visible, infrared);
        /*printf("\nFull spectrum: %d\n", visible + infrared);
        printf("Infrared:      %d\n", infrared);
        printf("Visible:       %d\n", visible);
        printf("Lux:           %d\n", tsl2561_compute_lux(tsl2561_info, visible, infrared));*/
	light_read();
	vTaskDelayUntil(&lLastWakeTime,lFrequency); 
    }
}

int light_write(){
	int send;
	send = lightValueRead;
	send = send*10;//the "name" for light is put into the ones' place, so need to multiply the read value by 10 to make room
	send = send+2; //the name of light is 2 
	pushQ(&send);
	//printf("\n |Light Write| Visible Light Value: %d\n", lightValueRead); //global variables are still bad practice
	return lightValueRead;
}

void light_close(){
	vTaskSuspend(handleLight);
}


void light_open()
{
	if(handleLight == NULL){ //on first call, define this task
    xTaskCreate(&tsl2561_task, "tsl2561_task", 2048, NULL, 5, handleLight);
	struct row lightRow;
	lightRow.read = light_read;
	lightRow.write = light_write;
	lightRow.name = 2;
	lightRow.open = light_open;
	lightRow.close = light_close;
	devTable[rowsInUse++] = lightRow;
    // I2C/SMBus Test application
    //extern void test_smbus_task(void * pvParameter);
    //xTaskCreate(&test_smbus_task, "test_smbus_task", 2048, NULL, 5, NULL);
	}else{ //on every other call, resume this task
 		vTaskResume(handleLight);
		
		}
	
	}
#endif
<file_sep>#include "DHT_main.c"
#include "light_main.c"
#include "qExample.c"
#include "sensor.c"
#include "fileTable.h"
#include "communications.c"
#include "command.c"

TaskHandle_t handleManage = NULL;
void manage_task();
int tempAvg;
int humidAvg;
int lightAvg;

gpio_num_t SUPERUSER_GPIO = GPIO_NUM_27; //variables to make them easier to change
char input[20];
char password[] = "<PASSWORD>";

int sort; //sort looks at the first digit off of top of queue, then sends it to correct averaging value

void app_main(){
	
	temp_open();
	humid_open(); //open all of the tasks we'll need and put them on the stack. We implemented it this way to make the Mnager more modular, but same idea as example code in class.
	light_open();
	
	q_app_main(); //these are data structures used by the manager to control the rest of the system.
	command_open();
	sense_open();
	comms_open();
	command_open();
	
	tempAvg = temp_write()/10; //then set initial values
	humidAvg = humid_write()/10;
	lightAvg = light_write()/10;
	nvs_flash_init();
	xTaskCreate( &manage_task, "ManageTask", 2048, NULL, 5, &handleManage );
}

void updateTempAvg(int toAdd){
	int tempTempAvg;
	toAdd = toAdd/10;
	tempAvg = 6*tempAvg; //weighted average: 60% current value, 40% new value
	toAdd = 4*toAdd;
	tempAvg += toAdd;
	tempAvg = tempAvg/10;
       	tempTempAvg = tempAvg*10;
	pushW(&tempTempAvg);
//	printf("\nWeighted Temperature Average: %d\n",tempAvg);
	
	//set temperature's signature value for command task
	if(tempAvg > 40){
		signature[0] = 2; //probably fire
	}else if(tempAvg > 25){
		signature[0] = 1; //hot summer day
	}else if(tempAvg > 20){
		signature[0] = 0; //20-25C is about room temperature
	}else if(tempAvg > 15){
		signature[0] = -1; //cold winter day outside
	}else
		signature[0] = -2; //terrifying apocalyptic event
	
}

void updateHumidAvg(int toAdd){
	int tempHumidAvg;
	toAdd = toAdd/10;
	humidAvg = 6*humidAvg; //weighted average: 60% current value, 40% new value
	toAdd = 4*toAdd;
	humidAvg += toAdd;
	humidAvg = humidAvg/10;
	tempHumidAvg = (humidAvg*10)+1;
	pushW(&tempHumidAvg);;
//	printf("\nWeighted Humidity Average: %d\n",humidAvg);
	
	if(humidAvg > 50){
		signature[1] = 2; //way too humid
	}else if(humidAvg > 40){
		signature[1] = 1; //still too humid but a believable amount
	}else if(humidAvg > 25){
		signature[1] = 0; //20-25C is about room temperature
	}else if(humidAvg > 15){
		signature[1] = -1; //dry day
	}else
		signature[1] = -2; //terrifying apocalyptic event

}

void updateLightAvg(int toAdd){
	
	int tempLightAvg;
	toAdd = toAdd/10;
	lightAvg = 6*(lightAvg)*(lightAvg); //weighted average: 60% current value, 40% new value
	toAdd = 4*toAdd;
	lightAvg += toAdd;
	lightAvg = lightAvg/10;
	tempLightAvg = (lightAvg*10)+2;
	pushW(&tempLightAvg);	
//	printf("\nWeighted Light Average: %d\n",lightAvg);
	
	if(lightAvg > 400){
		signature[2] = 2; //possible that the sun exploded
	}else if(lightAvg > 300){
		signature[2] = 1; //still too bright
	}else if(lightAvg > 200){
		signature[2] = 0; //I think this is normal? Need to calibrate this
	}else if(lightAvg > 100){
		signature[2] = -1; //normal night darkness
	}else
		signature[2] = -2; //terrifying apocalyptic event
}

void noUpdates(){
	printf("\nNo values found on queue this period.\n");
}

void manage_task(){
	int name; //name is the "name" of the sensor, put into the ones place for ease of reading
	int tableIndex;

	TickType_t xLastWakeTime;
	//every ten seconds, read off from the queue
	const TickType_t xFrequency = 15000*portTICK_RATE_MS;
	while(1){
	//to test that the functions are working properly
	xLastWakeTime = xTaskGetTickCount();
	
	for(tableIndex = 0; tableIndex < rowsInUse; tableIndex++){		
	sort = popQ();
	printf("\nManager Task: %d is popQ\n", sort);
	name = sort%10; //name is stored in ones' place of sort, so this works I think

	switch(name){
		case 0:
			updateTempAvg(sort);
			break;
		case 1:
			updateHumidAvg(sort);
			break;
		case 2: 
			updateLightAvg(sort);
			break;
		default:
			noUpdates();
			break;

			}//end switch case		
	
	


				
		}//end tableIndexing
	
		vTaskDelayUntil(&xLastWakeTime,xFrequency);

	}//end whileLoop for manager task
}//end manager task
<file_sep>/*	Create_DHT_Task.c	*/

#include "DHT_main.c"

// Buffer that the task being created will use as its stack.  Note this is
// an array of StackType_t variables.  The size of StackType_t is dependent on
// the RTOS port.

//Damon:I don't know how much stack DHT will need so this should go up/down as needed for different task implementations
int STACK_SIZE = 63;

StackType_t xStack[ STACK_SIZE ];

// Damon: These all start with the same priority I think, but maybe the ctl command is supposed to change that so I made it a variable
int DHT_priority = 10; 

// Damon: Function that creates a task. Each task needs its own unique creation function I think, unless we want to mess around with adding parameters to these.
// Damon: From what I understand, Manager task should create/destroy tasks as needed, and this is an example that should create a task using DHT_task()
void createDHTTask( void ) 
{
    TaskHandle_t xHandle = NULL;

    // Create the task without using any dynamic memory allocation.
	//Damon: This can be ported to the dynamic-memory task creation function if you guys want, I just chose the simpler one
    xHandle = xTaskCreateStatic(
                  DHT_task,       // Function that implements the task.
                  "DHT_Name",          // Text name for the task.
                  STACK_SIZE,      // Stack size in bytes, not words.
                  ( void * ) 1,    // Parameter passed into the task.
                  DHT_priority,		// Priority at which the task is created.
                  xStack,          // Array to use as the task's stack.
                  &xTaskBuffer );  // Variable to hold the task's data structure.

    // puxStackBuffer and pxTaskBuffer were not NULL, so the task will have
    // been created, and xHandle will be the task's handle.  Use the handle
    // to suspend the task.
    vTaskSuspend( xHandle );
}<file_sep># ece566
ESP-32 Projects as featured in ECE566 Course at IUPUI
<file_sep>/* This is the CA certificate for the CA trust chain of
   www.howsmyssl.com in PEM format, as dumped via:

   openssl s_client -showcerts -connect mqtt.iotcebu.com:8083 </dev/null

   The CA cert is the last cert in the chain output by the server.
*/
#include <stdio.h>
#include <stdint.h>
#include <string.h>

/*
 1 s:/C=US/O=Let's Encrypt/CN=Let's Encrypt Authority X3
   i:/O=Digital Signature Trust Co./CN=DST Root CA X3
 */
const char *server_root_cert = "-----BEGIN CERTIFICATE-----\r\n"
"<KEY>"
"<KEY>"
"<KEY>"
"<KEY>"
"<KEY>"
"<KEY>"
"<KEY>"
"<KEY>keh<KEY>"
"<KEY>"
"<KEY>"
"<KEY>"
"<KEY>"
"<KEY>"
"<KEY>"
"<KEY>"
"<KEY>"
"<KEY>"
"<KEY>"
"<KEY>"
"<KEY>"
"<KEY>"
"<KEY>"
"<KEY>"
"<KEY>"
"<KEY>"
"<KEY>"
"<KEY>"
"<KEY>"
"<KEY>"
"pu/xO28QOG8=\r\n"
"-----END CERTIFICATE-----\r\n";


<file_sep>#include "DHT_main.c"
#include "light_main.c"
#include "qExample.c"

TaskHandle_t handleSense = NULL;
void sense_task();

void sense_open(){
	nvs_flash_init();
	vTaskDelay( 1000 / portTICK_RATE_MS );
	xTaskCreate( &sense_task, "SenseTask", 2048, NULL, 5, &handleSense );
	
}

void sense_task(){
	int tableIndex;
		
		TickType_t sLastWakeTime;
		const TickType_t sFrequency = 15000*portTICK_RATE_MS;
	while(1){
		//sensor task just calls the write() functions, which push read values onto the shared queue
		sLastWakeTime = xTaskGetTickCount();
		for(tableIndex = 0; tableIndex < rowsInUse; tableIndex++){
			printf("\n|SENSE TASK| tableIndex = %d and read value is %d ", tableIndex, devTable[tableIndex].write()/10);
		}
	
	vTaskDelayUntil(&sLastWakeTime, sFrequency);
	}
}
<file_sep>/* 

	DHT22 temperature sensor driver

*/

#ifndef DHT22_H_  
#define DHT22_H_

#define DHT_OK 0
#define DHT_CHECKSUM_ERROR -1
#define DHT_TIMEOUT_ERROR -2

// == function prototypes =======================================

void 	setDHTgpio(int gpio);
void    setLEDgpio(int gpio); // Bree created to integrate her LED blinking for fun
void 	errorHandler(int response);
int 	readDHT();
float 	getHumidity();
float 	getTemperature();
int 	getSignalLevel( int usTimeOut, bool state );
float temps[10];
int usedtemps;
int tempRead;
int tempOpen;

#endif
