浏览代码

Merge remote-tracking branch 'refs/remotes/origin/developer' into GoToSleep

sandriek 9 年之前
父节点
当前提交
2e8f804aa7
共有 19 个文件被更改,包括 564 次插入1183 次删除
  1. 3 1
      .idea/InternetRadio.iml
  2. 23 5
      alarm.c
  3. 52 2
      contentparser.c
  4. 1 0
      contentparser.h
  5. 4 4
      displayHandler.c
  6. 18 14
      gotosleep.c
  7. 3 3
      gotosleep.h
  8. 58 80
      main.c
  9. 0 758
      mmcdrv.c
  10. 0 100
      mmcdrv.h
  11. 332 0
      mp3stream.c
  12. 25 0
      mp3stream.h
  13. 7 10
      network.c
  14. 7 1
      ntp.c
  15. 4 1
      ntp.h
  16. 0 151
      remcon.c
  17. 0 52
      remcon.h
  18. 26 0
      typedefs.h
  19. 1 1
      vs10xx.c

+ 3 - 1
.idea/InternetRadio.iml

@@ -1,7 +1,9 @@
 <?xml version="1.0" encoding="UTF-8"?>
 <module type="CPP_MODULE" version="4">
   <component name="NewModuleRootManager">
-    <content url="file://$MODULE_DIR$" />
+    <content url="file://$MODULE_DIR$">
+      <sourceFolder url="file://$MODULE_DIR$/CMakeLists.txt" isTestSource="false" />
+    </content>
     <orderEntry type="sourceFolder" forTests="false" />
     <orderEntry type="module-library">
       <library name="Header Search Paths">

+ 23 - 5
alarm.c

@@ -9,7 +9,7 @@
 #include "rtc.h"
 #include "alarm.h"
 #include "display.h"
-#include "httpstream.h"
+#include "mp3stream.h"
 
 #define n 5
 
@@ -71,7 +71,6 @@ void setSnooze(int idx){
 	alarm[idx].state = 2;
 	snooze[idx].snoozeTime = ct;
 	snooze[idx].snoozeTime.tm_min += alarm[idx].snooze;
-	stopStream();
 }
 
 int daysInMonth(int m, int y) {
@@ -124,7 +123,16 @@ void setState(int idx){
 	}
 	
 	if (compareTime(ct, alarm[idx].time) >= 1 && alarm[idx].time.tm_year != 0 && alarm[idx].state != 2){
-		alarm[idx].state = 1;
+		if(alarm[idx].state != 1) {
+			alarm[idx].state = 1;
+			printf("\n\nAlarm gaat nu af!\n\n");
+			bool success = connectToStream(alarm[idx].ip, alarm[idx].port, alarm[idx].url);
+			if (success == true){
+				play();
+			}else {
+				printf("ConnectToStream failed. Aborting.\n\n");
+			}
+		}
 	} else if (alarm[idx].state != 2){
 		alarm[idx].state = 0;
 	}
@@ -138,11 +146,20 @@ void setState(int idx){
 		snooze[idx].snoozeTime = ct;
 		AddSnoozeMinutes(idx, alarm[idx].snooze);
 		LcdBackLight(LCD_BACKLIGHT_OFF);
-		stopStream();
+		killPlayerThread();
 	}
 	
 	if (alarm[idx].state == 2 && compareTime(ct, snooze[idx].snoozeTime) >= 1){
-		alarm[idx].state = 1;
+		if(alarm[idx].state != 1){
+			printf("Alarm komt nu uit snooze!!");
+			bool success = connectToStream(alarm[idx].ip, alarm[idx].port, alarm[idx].url);
+			if (success == true){
+				play();
+			}else {
+				printf("ConnectToStream failed. Aborting.\n\n");
+			}
+			alarm[idx].state = 1;
+		}
 		AddSnoozeMinutes(idx, 1);
 	}
 }
@@ -181,6 +198,7 @@ void deleteAlarm(int idx){
 void handleAlarm(int idx){
 	alarm[idx].state = 0;
 	alarm[idx].time.tm_mday += 1;
+	killPlayerThread();
 	printf("state is %d \n",alarm[idx].state);
 }
 

+ 52 - 2
contentparser.c

@@ -5,14 +5,16 @@
 #include "ntp.h"
 #include "network.h"
 #include "jsmn.h"
+#include "mp3stream.h"
 #include "rtc.h"
 #include "alarm.h"
+#include "vs10xx.h"
 
 void parseAlarmJson(char* content){
     int r;
     int i = 2;
     jsmn_parser p;
-    jsmntok_t token[150]; /* We expect no more than 128 tokens */
+    jsmntok_t token[160]; /* We expect no more than 128 tokens */
 
     jsmn_init(&p);
     r = jsmn_parse(&p, content, strlen(content), token, sizeof(token)/sizeof(token[0]));
@@ -37,6 +39,7 @@ void parseAlarmJson(char* content){
         char ip[24];
         char name[16];
         char st = -1;
+        char oo = -1;
         memset(url, 0, 24);
         memset(ip, 0, 24);
         memset(name, 0, 17);
@@ -64,6 +67,8 @@ void parseAlarmJson(char* content){
                 getStringToken(content, &token[i + 1], url);
             }else if (jsoneq(content, &token[i], "name") == 0) {
                 getStringToken(content, &token[i + 1], name);
+            }else if (jsoneq(content, &token[i], "oo") == 0) {
+                getStringToken(content, &token[i + 1], oo);
             }else if (jsoneq(content, &token[i], "st") == 0) {
                 st = getIntegerToken(content, &token[i + 1]);
                 i+=2;
@@ -97,8 +102,53 @@ void parseAlarmJson(char* content){
     }
 }
 
+void parseCommandQue(char* content){
+    int r;
+    int i;
+    jsmn_parser p;
+    jsmntok_t token[150]; /* We expect no more than 128 tokens */
+
+    jsmn_init(&p);
+    r = jsmn_parse(&p, content, strlen(content), token, sizeof(token)/sizeof(token[0]));
+    if (r <= 0) {
+        printf("Failed to parse JSON: %d \n", r);
+        return;
+    }else{
+        printf("Aantal tokens found: %d \n", r);
+    }
+
+    for(i = 0; i < r; i++)
+    {
+        if (jsoneq(content, &token[i], "command") == 0) {
+            if(jsoneq(content, &token[i + 1], "volume") == 0){
+                char vol = getIntegerToken(content, &token[i + 3]);
+                vol = 128 - ((vol * 128) / 100);
+                VsSetVolume(vol, vol);
+                i += 3;
+            }else if(jsoneq(content, &token[i + 1], "stopstream") == 0){
+                killPlayerThread();
+                i += 3;
+            }else if(jsoneq(content, &token[i + 1], "startstream") == 0){
+                u_short port = getIntegerToken(content, &token[i + 9]);
+                char url[24];
+                char ip[24];
+                getStringToken(content, &token[i + 7], url);
+                getStringToken(content, &token[i + 5], ip);
+                bool success = connectToStream(ip, port, url);
+                if (success == true){
+                    play();
+                }else {
+                    printf("ConnectToStream failed. Aborting.\n\n");
+                }
+                i += 9;
+            }
+        }
+    }
+}
+
 void parsetimezone(char* content)
 {
     int timezone = atoi(content);
-    printf("%d", timezone);
+    setTimeZone(timezone);
 }
+

+ 1 - 0
contentparser.h

@@ -5,6 +5,7 @@
 #define CONTENTPARSER_H
 
 void parseAlarmJson(char* content);
+void parseCommandQue(char* content);
 void parsetimezone(char* content);
 
 #endif //CONTENTPARSER_H

+ 4 - 4
displayHandler.c

@@ -14,7 +14,6 @@
 #include "rtc.h"
 #include "alarm.h"
 #include "network.h"
-#include "httpstream.h"
 
 #define MONTH_OFFSET 1
 #define YEAR_OFFSET 1900
@@ -67,12 +66,11 @@ void displayAlarm(int line_number, int line_numberTwo, int idx)
 	int startidx;
     char str[16];
 	struct _alarm am = getAlarm(idx);
-	
+
     sprintf(str, "    %02d:%02d:%02d    ", am.time.tm_hour, am.time.tm_min, am.time.tm_sec);
     if (line_number > -1 && line_number < 2){
         (*write_display_ptr[line_number])(str, 16);
     }
-    playStream(am.ip, am.port, am.url);
 
 	j = 0;
     char str2[16];
@@ -81,7 +79,7 @@ void displayAlarm(int line_number, int line_numberTwo, int idx)
 			j = j + 1;
 		}
 	}
-	
+
 	if (j != 16){
 		startidx = (8-(j/2));
 	}
@@ -102,6 +100,8 @@ void displayAlarm(int line_number, int line_numberTwo, int idx)
         (*write_display_ptr[line_numberTwo])(str2, 16);
         LcdBackLight(LCD_BACKLIGHT_ON);
     }
+
+
 }
 
 void displayVolume(int pos)

+ 18 - 14
gotosleep.c

@@ -10,49 +10,53 @@
 #include "alarm.h"
 #include "display.h"
 #include "httpstream.h"
+#include "mp3stream.h"
 #include "gotosleep.h"
 struct _fallSleep
 {
 	struct _tm sleepTime;
 };
 struct _tm count;
-int i = 0;
-void setSleep()
+int i = 1;
+int x = 0;
+void setSleep(void)
 {
 	X12RtcGetClock(&count);
 	fallSleep.sleepTime = count;
 	fallSleep.sleepTime.tm_hour += 1;
 	changeChanel();
+	x = fallSleep.sleepTime.tm_min;
 	return 1;
 }
-void checkSleep(int vol1)
+void checkSleep(void)
 {
 	X12RtcGetClock(&count);
 	if(compareTime(count, fallSleep.sleepTime) == 0){
-		stopStream();
-		i = 0;
+		killPlayerThread(); 
+	}
+	if(compareTime(count, fallSleep.sleepTime) == 5 && fallSleep.sleepTime.tm_min == x){
+		volumeDown();
+		x += 2;
 	}
 	return 1;
 }
-void changeChanel(){
+void changeChanel(void){
 	
 	if (i > 2){
 		i =1;
 	}
 	switch(i) {
-	case 0  :
-      playStream("62.195.226.247",80,"/test.mp3");
-	  i = 2;
-      break;
    case 1  :
-	  stopStream(); 
-      playStream("62.195.226.247",80,"/test.mp3");
+	  killPlayerThread(); 
+      connectToStream("62.195.226.247",80,"/test.mp3");
+	  play();
 	  i++;
       break;
 	
    case 2  :
-      stopStream(); 
-      playStream("62.195.226.247",80,"/test2.mp3");
+	  killPlayerThread(); 
+      connectToStream("62.195.226.247",80,"/test2.mp3");
+	  play()
 	  i++;
       break;
 }

+ 3 - 3
gotosleep.h

@@ -1,6 +1,6 @@
 #ifndef _GoToSleep_H
 #define _GoToSleep_H
-extern void setSleep();
-extern void checkSleep();
-extern void changeChanel();
+extern void setSleep(void);
+extern void checkSleep(void);
+extern void changeChanel(void);
 #endif

+ 58 - 80
main.c

@@ -20,36 +20,33 @@
 /*--------------------------------------------------------------------------*/
 #include <stdio.h>
 #include <string.h>
+#include <time.h>
 
 #include <sys/thread.h>
 #include <sys/timer.h>
 #include <sys/version.h>
 #include <dev/irqreg.h>
 
-#include "displayHandler.h"
-#include "system.h"
-#include "portio.h"
+// Note: Please keep the includes in alphabetical order!    - Jordy
+#include "alarm.h"
+#include "contentparser.h"
 #include "display.h"
-#include "remcon.h"
+#include "displayHandler.h"
+#include "gotosleep.h"
 #include "keyboard.h"
 #include "led.h"
 #include "log.h"
-#include "uart0driver.h"
-#include "mmc.h"
-#include "watchdog.h"
-#include "flash.h"
-#include "spidrv.h"
+#include "mp3stream.h"
 #include "network.h"
+#include "ntp.h"
+#include "portio.h"
+#include "rtc.h"
+#include "spidrv.h"
+#include "system.h"
 #include "typedefs.h"
+#include "uart0driver.h"
+#include "watchdog.h"
 
-
-#include <time.h>
-#include "rtc.h"
-#include "alarm.h"
-#include "ntp.h"
-#include "httpstream.h"
-#include "contentparser.h"
-#include "gotosleep.h"
 /*-------------------------------------------------------------------------*/
 /* local routines (prototyping)                                            */
 /*-------------------------------------------------------------------------*/
@@ -86,10 +83,13 @@ static void SysMainBeatInterrupt(void *p)
 {
 
     /*
-     *  scan for valid keys AND check if a MMCard is inserted or removed
+     *  scan for valid keys
      */
     KbScan();
-    CardCheckCard();
+
+    if(KbGetKey() != KEY_NO_KEY){
+        LcdBackLight(LCD_BACKLIGHT_ON);
+    }
 }
 
 /*!
@@ -182,10 +182,9 @@ static void SysControlMainBeat(u_char OnOff)
 /*-------------------------------------------------------------------------*/
 /* global variable definitions                                             */
 /*-------------------------------------------------------------------------*/
-int isAlarmSyncing;
-int initialized;
-int running = 0;
-unsigned char VOL = 64;
+bool isAlarmSyncing = false;
+bool initialized = false;
+bool running = false;
 
 /*-------------------------------------------------------------------------*/
 /* local variable definitions                                              */
@@ -196,41 +195,38 @@ unsigned char VOL = 64;
 /*-------------------------------------------------------------------------*/
 THREAD(StartupInit, arg)
 {
+    NutThreadSetPriority(5);
+
     NetworkInit();
 
-    NtpSync();
+    initialized = true;
 
-    initialized = 1;
     NutThreadExit();
 }
 
-THREAD(NTPSync, arg)
+THREAD(AlarmSync, arg)
 {
-    for(;;)
-    {
-        if(initialized && (hasNetworkConnection() == true))
-        {
-            while(isAlarmSyncing)
-            {
-                NutSleep(2000);
-            }
-            NtpSync();
-        }
-        NutSleep(86400000);
+    NutThreadSetPriority(50);
+
+    while(initialized == false){
+        NutSleep(1000);
     }
-}
 
-THREAD(AlarmSync, arg)
-{
+    NtpSync();
+
     for(;;)
     {
-        if(initialized && (hasNetworkConnection() == true))
+        if((initialized == true) && (hasNetworkConnection() == true))
         {
-            isAlarmSyncing = 1;
-            char url[43];
-            sprintf(url, "%s%s", "/getAlarmen.php?radiomac=", getMacAdress());
+            isAlarmSyncing = true;
+            char url[49];
+            sprintf(url, "/getAlarmen.php?radiomac=%s&tz=%d", getMacAdress(), getTimeZone());
             httpGet(url, parseAlarmJson);
-            isAlarmSyncing = 0;
+            isAlarmSyncing = false;
+
+            //Command que (Telegram) sync
+            sprintf(url, "%s%s", "/getCommands.php?radiomac=", getMacAdress());
+            httpGet(url, parseCommandQue);
         }
         NutSleep(3000);
     }
@@ -269,8 +265,6 @@ int checkOffPressed(){
 
 int main(void)
 {
-	initialized = 0;
-    int VOL2 = 127;
     struct _tm timeCheck;
 	struct _tm start;
 	int idx = 0;
@@ -291,22 +285,17 @@ int main(void)
     Uart0DriverStart();
 	LogInit();
 
-    CardInit();
-
     X12Init();
 
     VsPlayerInit();
 
- 
-    NtpInit();
+     NtpInit();
 
     NutThreadCreate("BackgroundThread", StartupInit, NULL, 1024);
     NutThreadCreate("BackgroundThread", AlarmSync, NULL, 2500);
-    NutThreadCreate("BackgroundThread", NTPSync, NULL, 700);
+    //NutThreadCreate("BackgroundThread", NTPSync, NULL, 700);
     /** Quick fix for turning off the display after 10 seconds boot */
 
-    RcInit();
-
 	KbInit();
 
     SysControlMainBeat(ON);             // enable 4.4 msecs heartbeat interrupt
@@ -318,9 +307,6 @@ int main(void)
 
 	/* Enable global interrupts */
 	sei();
-
-
-
 	
 	LcdBackLight(LCD_BACKLIGHT_OFF);
 	X12RtcGetClock(&timeCheck);
@@ -341,38 +327,33 @@ int main(void)
 		//Check if a button is pressed
 		if (checkOffPressed() == 1){
 			X12RtcGetClock(&start);
-			running = 1;
+			running = true;
             LcdBackLight(LCD_BACKLIGHT_ON);
 		}
 
 		//Check if background LED is on, and compare to timer
-		if (running == 1){
-			if (timerStruct(start) >= 10 || running > 1){
-				running = 0;
+		if (running == true){
+			if (timerStruct(start) >= 10){
+				running = false;
 				LcdBackLight(LCD_BACKLIGHT_OFF);
 			}
 		}
 
-        VOL = VOL2;
         if(KbGetKey() == KEY_DOWN)
         {
             NutSleep(150);
-             X12RtcGetClock(&timeCheck);
-            if(VOL > 8){
-                VOL -= 8;
-                VsSetVolume (127-VOL, 127-VOL);
-                displayVolume(VOL/8);
-            }
+            X12RtcGetClock(&timeCheck);
+
+            u_char newVolume = volumeDown();
+            displayVolume((int)newVolume);
         }
         else if(KbGetKey() == KEY_UP)
         {
             NutSleep(150);
-             X12RtcGetClock(&timeCheck);
-            if(VOL < 128) {
-                VOL += 8;
-                VsSetVolume(128-VOL, 128-VOL);
-                displayVolume(VOL/8);
-            }
+            X12RtcGetClock(&timeCheck);
+
+            u_char newVolume = volumeUp();
+            displayVolume((int)newVolume);
         }
 		else if(KbGetKey() == KEY_LEFT)
         {
@@ -397,12 +378,11 @@ int main(void)
 						handleAlarm(idx);
 						//NutDelay(50);
 						LcdBackLight(LCD_BACKLIGHT_OFF);
-                        stopStream();
-					} else if (KbGetKey() == KEY_01 || KbGetKey() == KEY_02 || KbGetKey() == KEY_03 || KbGetKey() == KEY_04 || KbGetKey() == KEY_05 || KbGetKey() == KEY_ALT){
+                    } else if (KbGetKey() == KEY_01 || KbGetKey() == KEY_02 || KbGetKey() == KEY_03 || KbGetKey() == KEY_04 || KbGetKey() == KEY_05 || KbGetKey() == KEY_ALT){
 						setSnooze(idx);
 						LcdBackLight(LCD_BACKLIGHT_OFF);
-                        stopStream();
-					}
+                        killPlayerThread();
+                    }
 				}
 			}
 		}
@@ -410,8 +390,6 @@ int main(void)
             displayTime(0);
             displayDate(1);
 		}
-		checkSleep();
-        VOL2 = VOL;
         WatchDogRestart();
     }
     return(0);

+ 0 - 758
mmcdrv.c

@@ -1,758 +0,0 @@
-/****************************************************************************
-*  This file is part of the MMC device driver.
-*
-*  Copyright (c) 2004 by Michael Fischer. All rights reserved.
-*
-*  Thanks to Sylvain Bissonnette for some of his low level functions.
-*  Take a look at www.microsyl.com (Led Sign with MMC MemoryCard)
-*
-*  Redistribution and use in source and binary forms, with or without
-*  modification, are permitted provided that the following conditions
-*  are met:
-*
-*  1. Redistributions of source code must retain the above copyright
-*     notice, this list of conditions and the following disclaimer.
-*  2. Redistributions in binary form must reproduce the above copyright
-*     notice, this list of conditions and the following disclaimer in the
-*     documentation and/or other materials provided with the distribution.
-*  3. Neither the name of the author nor the names of its contributors may
-*     be used to endorse or promote products derived from this software
-*     without specific prior written permission.
-*
-*  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
-*  "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
-*  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
-*  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL
-*  THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
-*  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
-*  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
-*  OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
-*  AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
-*  OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF
-*  THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
-*  SUCH DAMAGE.
-*
-****************************************************************************
-*  History:
-*
-*  10.10.04  mifi   First Version
-****************************************************************************/
-#define __MMCDRV_C__
-
-#define LOG_MODULE  LOG_MMCDRV_MODULE
-
-#include <stdio.h>
-#include <string.h>
-
-#include <sys/timer.h>
-#include <sys/thread.h>
-#include <sys/event.h>
-#include <sys/heap.h>
-
-#include "typedefs.h"
-#include "portio.h"
-#include "mmcdrv.h"
-#include "vs10xx.h"
-#include "led.h"
-#include "log.h"
-#include "spidrv.h"
-
-/*==========================================================*/
-/*  DEFINE: All Structures and Common Constants             */
-/*==========================================================*/
-#define MMC_MAX_SUPPORTED_DEVICE    1
-
-/*
- * Drive Flags
- */
-#define MMC_SUPPORT_LBA             0x0001
-#define MMC_SUPPORT_LBA48           0x0002
-
-#define MMC_READ_ONLY               0x4000
-#define MMC_READY                   0x8000
-
-#define Delay_1ms(_x) NutDelay(_x)
-
-#define SPIDDR        DDRB
-#define SPIPORT       PORTB
-#define SPIPIN        PINB
-
-/*
-    PragmaLab: disable PIN-defines (already defined in 'portio.h'
-#define SCLK          0x02
-#define MOSI          0x04
-#define MISO          0x08
-#define CS            0x20
-#define ENABLE        0x40
-    end PragmaLab
-*/
-
-#define MMC_RESET         0
-#define MMC_INIT          1
-#define MMC_READ_CSD    9
-#define MMC_READ_CID    10
-
-typedef struct _drive
-{
-    /*
-     * Interface values
-     */
-    WORD  wFlags;
-    BYTE  bDevice;
-
-    /*
-     * LBA value
-     */
-    DWORD dTotalSectors;
-    WORD  wSectorSize;
-} DRIVE;
-
-/*==========================================================*/
-/*  DEFINE: Definition of all local Data                    */
-/*==========================================================*/
-static HANDLE          hMMCSemaphore;
-static DRIVE           sDrive[MMC_MAX_SUPPORTED_DEVICE];
-
-static MMC_MOUNT_FUNC *pUserMountFunc;
-static MMC_MOUNT_FUNC *pUserUnMountFunc;
-
-/*==========================================================*/
-/*  DEFINE: Definition of all local Procedures              */
-/*==========================================================*/
-
-
-/************************************************************/
-/*  MMCLock                                                 */
-/************************************************************/
-static void MMCLock(void)
-{
-    NutEventWait(&hMMCSemaphore, 0);
-} /* MMCLock */
-
-/************************************************************/
-/*  MMCFree                                                 */
-/************************************************************/
-static void MMCFree(void)
-{
-    NutEventPost(&hMMCSemaphore);
-} /* MMCFree */
-
-/************************************************************/
-/*  MMCSemaInit                                             */
-/************************************************************/
-static void MMCSemaInit(void)
-{
-    NutEventPost(&hMMCSemaphore);
-} /* MMCSemaInit */
-
-
-/************************************************************
- * int MMCDataToken(void)
- *
- * - pings the card until it gets data token
- * - returns one byte of read info (data token)
- ************************************************************/
-static BYTE MMCDataToken(void)
-{
-    WORD i = 0xffff;
-    BYTE Byte = 0xff;
-
-    while ((Byte != 0xfe) && (--i))
-    {
-        Byte = SPIgetByte();
-    }
-    return(Byte);
-} /* MMCDataToken */
-
-/************************************************************
- * unsigned char MMCGet(void)
- *
- * - pings the card until it gets a non-0xff value
- * - returns one byte of read info
- ************************************************************/
-static BYTE MMCGet(void)
-{
-    WORD i = 0xffff;
-    BYTE Byte = 0xff;
-
-    while ((Byte == 0xff) && (--i))
-    {
-        Byte = SPIgetByte();
-    }
-
-    return(Byte);
-} /* MMCGet */
-
-/************************************************************
- * void MMCCommand(unsigned char command, unsigned int px, unsigned int py)
- *
- * - send one byte of 0xff, then issue command + params + (fake) crc
- * - eat up the one command of nothing after the CRC
- ************************************************************/
-static void MMCCommand(unsigned char command, unsigned int px, unsigned int py)
-{
-    SPIselect(SPI_DEV_MMC);
-
-    SPIputByte(0xff);
-    SPIputByte(command | 0x40);
-    SPIputByte((unsigned char)((px >> 8)&0x0ff)); /* high byte of param y */
-    SPIputByte((unsigned char)(px & 0x00ff));     /* low byte of param y */
-    SPIputByte((unsigned char)((py >> 8)&0x0ff)); /* high byte of param x */
-    SPIputByte((unsigned char)(py & 0x00ff));     /* low byte of param x */
-    SPIputByte(0x95);            /* correct CRC for first command in SPI          */
-                              /* after that CRC is ignored, so no problem with */
-                              /* always sending 0x95                           */
-    SPIputByte(0xff);
-} /* MMCCommand */
-
-/************************************************************/
-/* GetCSD                                                   */
-/************************************************************/
-static int GetCSD (DRIVE *pDrive)
-{
-    int   i;
-    int  nError = MMC_ERROR;
-    BYTE bData[16];
-    WORD wREAD_BL_LEN;
-    WORD wC_SIZE;
-    WORD wC_SIZE_MULT;
-    WORD wDummy;
-    DWORD dTotalSectors = 0;
-
-    MMCCommand(MMC_READ_CSD, 0, 0);
-    if (MMCDataToken() != 0xfe)
-    {
-        LogMsg_P(LOG_ERR, PSTR("error during CSD read"));
-    }
-    else
-    {
-        for (i=0; i<16; i++)
-        {
-            bData[i] = SPIgetByte();
-        }
-
-        SPIputByte(0xff);    /* checksum -> don't care about it for now */
-        SPIputByte(0xff);    /* checksum -> don't care about it for now */
-
-        SPIdeselect();
-
-        /*
-         * Get the READ_BL_LEN
-         */
-        wREAD_BL_LEN = (1 << (bData[5] & 0x0F));
-
-        /*
-         * Get the C_SIZE
-         */
-        wC_SIZE  = (bData[6] & 0x03);
-        wC_SIZE  = wC_SIZE << 10;
-
-        wDummy   = bData[7];
-        wDummy   = wDummy << 2;
-        wC_SIZE |= wDummy;
-
-        wDummy   = (bData[8] & 0xC0);
-        wDummy   = wDummy >> 6;
-        wC_SIZE |= wDummy;
-
-        /*
-         * Get the wC_SIZE_MULT
-         */
-        wC_SIZE_MULT  = (bData[9] & 0x03);
-        wC_SIZE_MULT |= wC_SIZE_MULT << 1;
-        wDummy        = (bData[10] & 0x80);
-        wDummy        = wDummy >> 7;
-        wC_SIZE_MULT |= wDummy;
-        wC_SIZE_MULT  = (1 << (wC_SIZE_MULT+2));
-
-        dTotalSectors  = wC_SIZE+1;
-        dTotalSectors *= wC_SIZE_MULT;
-
-        pDrive->dTotalSectors = dTotalSectors;
-        pDrive->wSectorSize   = wREAD_BL_LEN;
-
-        nError = MMC_OK;
-    }
-
-    return(nError);
-} /* GetCSD */
-
-#if 0
-/************************************************************/
-/* GetCID                                                   */
-/************************************************************/
-static void GetCID(void)
-{
-    int i;
-    BYTE bData[16];
-
-    MMCCommand(MMC_READ_CID, 0, 0);
-    if (MMCDataToken() != 0xfe)
-    {
-        printf("MMC: error during CID read\n");
-    }
-    else
-    {
-        printf("MMC: CID read\n");
-    }
-
-    for (i=0; i<16; i++)
-    {
-        bData[i] = SPIgetByte();
-    }
-
-    SPIputByte(0xff);    /* checksum -> don't care about it for now */
-    SPIputByte(0xff);    /* checksum -> don't care about it for now */
-
-    SPIdeselect();
-
-    printf("MMC: Product Name: %c%c%c%c%c%c\n",
-           bData[3], bData[4], bData[5],
-           bData[6], bData[7], bData[8]);
-} /* GetCID */
-#endif
-
-/************************************************************/
-/*  InitMMCCard                                             */
-/*                                                          */
-/* - flushes card receive buffer                            */
-/* - selects card                                           */
-/* - sends the reset command                                */
-/* - sends the initialization command, waits for card ready */
-/************************************************************/
-static int InitMMCCard(void)
-{
-    WORD i;
-
-    /* PragmaLab: disable initit of PINS and SPI, already done in 'SystemInitIO()'
-    SPIDDR = SCLK + MOSI + CS;
-    SPIPORT = 0x00;
-    Delay_1ms(250);
-    Delay_1ms(250);
-    SPIPORT |= CS;
-    SPCR = (1 << SPE) | (1 << MSTR);  // enable SPI as master, set clk divider
-                                      // set to max speed
-    Delay_1ms(250);
-
-
-    SPIdeselect();
-
-    // start off with 80 bits of high data with card deselected
-
-    PragmaLab: why send dummy bytes with card DEselected? This messes up the VS10XX init */
-    for (i = 0; i < 10; i++)
-    {
-        SPIputByte(0xff);
-    }
-
-    /*end PragmaLab */
-
-    /* send CMD0 - go to idle state */
-    MMCCommand(MMC_RESET, 0, 0);
-
-    if (MMCGet() != 1)
-    {
-        SPIdeselect();
-        return(MMC_ERROR);  // MMC Not detected
-    }
-
-    /* send CMD1 until we get a 0 back, indicating card is done initializing */
-    i = 0xffff;
-    while ((SPIgetByte() != 0) && (--i))
-    {
-        MMCCommand(MMC_INIT, 0, 0);
-    }
-    if (i == 0)
-    {
-        SPIdeselect();
-        return(MMC_ERROR);  // Init Fail
-    }
-
-    SPIdeselect();
-    return(MMC_OK);
-} /* InitMMCCard */
-
-/************************************************************/
-/*  ReadSectors                                             */
-/************************************************************/
-static int ReadSectors(DRIVE *pDrive, BYTE *pBuffer, DWORD dStartSector, WORD wSectorCount)
-{
-    int   nError = MMC_OK;
-    int   nSector;
-    WORD  wDataCount;
-    DWORD dReadSector;
-
-    pDrive = pDrive;
-
-    for (nSector=0; nSector<wSectorCount; nSector++)
-    {
-        dReadSector = dStartSector + nSector;
-
-        MMCCommand(17,(dReadSector>>7) & 0xffff, (dReadSector<<9) & 0xffff);
-        if (MMCDataToken() != 0xfe)
-        {
-            nError = MMC_ERROR;
-            SPIdeselect();
-            break;
-        }
-
-        for (wDataCount=0; wDataCount<512; wDataCount++)
-        { /* read the sector */
-            *pBuffer = SPIgetByte();
-            pBuffer++;
-        }
-
-        SPIputByte(0xff);    /* checksum -> don't care about it for now */
-        SPIputByte(0xff);    /* checksum -> don't care about it for now */
-        SPIdeselect();
-    }
-
-    return(nError);
-} /* ReadSectors */
-
-#if (MMC_SUPPORT_WRITE == 1)
-/************************************************************/
-/*  WriteSectors                                            */
-/************************************************************/
-static BYTE WriteSectors(DRIVE *pDrive, BYTE *pBuffer, DWORD dStartSector, WORD wSectorCount)
-{
-    int   nError = MMC_OK;
-    int   nSector;
-    WORD  wDataCount;
-    DWORD dWriteSector;
-
-    pDrive = pDrive;
-
-    for (nSector=0; nSector<wSectorCount; nSector++)
-    {
-        dWriteSector = dStartSector + nSector;
-
-        MMCCommand(24, (dWriteSector>>7)& 0xffff, (dWriteSector<<9)& 0xffff);
-        if (MMCGet() == 0xff)
-        {
-            nError = MMC_ERROR;
-            SPIdeselect();
-            break;
-        }
-
-        SPIputByte(0xfe);  // Send Start Byte
-
-        for (wDataCount=0; wDataCount<512; wDataCount++)
-        { /* read the sector */
-            SPIputByte(*pBuffer);
-            pBuffer++;
-        }
-
-        SPIputByte(0xff);  /* checksum -> don't care about it for now */
-        SPIputByte(0xff);  /* checksum -> don't care about it for now */
-        SPIputByte(0xff);  /* Read "data response byte"               */
-
-        wDataCount = 0xffff;
-        while ((SPIgetByte() == 0x00) && (--wDataCount)); /* wait for write finish */
-        if (wDataCount == 0)
-        {
-            nError = MMC_ERROR;
-            SPIdeselect();
-            break;
-        }
-
-        SPIdeselect();
-    }
-
-    return(nError);
-}
-#endif /* WriteSectors */
-
-/*==========================================================*/
-/*  DEFINE: All code exported                               */
-/*==========================================================*/
-/************************************************************/
-/*  MMCInit                                                 */
-/************************************************************/
-int MMCInit(int nMMCMode, MMC_MOUNT_FUNC *pMountFunc,
-            MMC_MOUNT_FUNC *pUnMountFunc)
-{
-    int  nError = MMC_OK;
-    BYTE bIndex;
-
-    nMMCMode         = nMMCMode;
-    pUserMountFunc   = pMountFunc;
-    pUserUnMountFunc = pUnMountFunc;
-
-    for (bIndex=0; bIndex<MMC_MAX_SUPPORTED_DEVICE; bIndex++)
-    {
-        memset((BYTE *) & sDrive[bIndex], 0x00, sizeof(DRIVE));
-
-        sDrive[bIndex].bDevice  = bIndex;
-    }
-
-    MMCSemaInit();
-
-    nError = InitMMCCard();
-    if (nError == MMC_OK)
-    {
-        sDrive[MMC_DRIVE_C].wFlags = MMC_READY;
-        //GetCID();
-    }
-
-    return(nError);
-} /* MMCInit */
-
-/************************************************************/
-/*  MMCMountAllDevices                                      */
-/************************************************************/
-int MMCMountAllDevices(int nMMCMode, BYTE *pSectorBuffer)
-{
-    int    nError = MMC_ERROR;
-    DRIVE *pDrive;
-
-    nMMCMode = nMMCMode;
-
-    pDrive = NULL;
-
-    MMCLock();
-
-    pDrive = &sDrive[MMC_DRIVE_C];
-    if (pDrive->wFlags & MMC_READY)
-    {
-        nError = GetCSD(pDrive);
-    }
-
-    MMCFree();
-
-    if (nError == MMC_OK)
-    {
-        nError = MMCReadSectors(MMC_DRIVE_C, pSectorBuffer, 0, 1);
-    }
-
-    return(nError);
-} /* MMCMountDevice */
-
-/************************************************************/
-/*  MMCGetSectorSize                                        */
-/************************************************************/
-int MMCGetSectorSize(BYTE bDevice)
-{
-    int    nSectorSize;
-    DRIVE *pDrive;
-
-    nSectorSize = 0;
-
-    MMCLock();
-
-    if (bDevice >= MMC_MAX_SUPPORTED_DEVICE)
-    {
-        nSectorSize = 0;
-    }
-    else
-    {
-        pDrive = &sDrive[bDevice];
-        nSectorSize = pDrive->wSectorSize;
-    }
-
-    MMCFree();
-
-    return(nSectorSize);
-} /* MMCGetSectorSize */
-
-/************************************************************/
-/*  MMCIsCDROMDevice                                        */
-/************************************************************/
-int MMCIsCDROMDevice(BYTE bDevice)
-{
-    return(FALSE);
-} /* MMCIsCDROMDevice */
-
-/************************************************************/
-/*  MMCIsZIPDevice                                          */
-/************************************************************/
-int MMCIsZIPDevice(BYTE bDevice)
-{
-    return(FALSE);
-} /* MMCIsZIPDevice */
-
-/************************************************************/
-/*  MMCUnMountDevice                                        */
-/************************************************************/
-int MMCUnMountDevice(BYTE bDevice)
-{
-    return(MMC_OK);
-} /* MMCUnMountDevice */
-
-/************************************************************/
-/*  MMCGetTotalSectors                                      */
-/************************************************************/
-DWORD MMCGetTotalSectors(BYTE bDevice)
-{
-    DWORD  dwTotalSectors;
-    DRIVE *pDrive;
-
-    dwTotalSectors = 0;
-
-    MMCLock();
-
-    if (bDevice >= MMC_MAX_SUPPORTED_DEVICE)
-    {
-        dwTotalSectors = 0;
-    }
-    else
-    {
-        pDrive = &sDrive[bDevice];
-        dwTotalSectors = pDrive->dTotalSectors;
-
-        //dwTotalSectors -= 64;
-    }
-
-    MMCFree();
-
-    return(dwTotalSectors);
-} /* MMCGetTotalSectors */
-
-/************************************************************/
-/*  MMCReadSectors                                          */
-/************************************************************/
-int MMCReadSectors(BYTE bDevice, void *pData, DWORD dwStartSector, WORD wSectorCount)
-{
-    int    nError;
-    WORD   wReadCount;
-    DRIVE *pDrive = 0;
-    BYTE  *pByte;
-
-    nError = MMC_OK;
-
-    MMCLock();
-
-    if (bDevice >= MMC_MAX_SUPPORTED_DEVICE)
-    {
-        nError = MMC_DRIVE_NOT_FOUND;
-    }
-    else
-    {
-        pDrive = &sDrive[bDevice];
-        if ((pDrive->wFlags & MMC_READY) == 0)
-        {
-            nError = MMC_DRIVE_NOT_FOUND;
-        }
-        else
-        {
-            if ((dwStartSector + wSectorCount) > pDrive->dTotalSectors)
-            {
-                nError = MMC_PARAM_ERROR;
-            }
-        }
-    }
-
-    if (nError == MMC_OK)
-    {
-        pByte = (BYTE *)pData;
-
-        if (wSectorCount != 1)
-        {
-            while (wSectorCount > 0)
-            {
-
-                if (wSectorCount < 256)
-                {
-                    wReadCount = wSectorCount;
-                }
-                else
-                {
-                    wReadCount = 256;
-                }
-
-                nError = ReadSectors(pDrive, pByte, dwStartSector, wReadCount);
-                if (nError != MMC_OK)
-                {
-                    break;
-                }
-
-                dwStartSector += wReadCount;
-                wSectorCount -= wReadCount;
-                pByte += (wReadCount * pDrive->wSectorSize);
-            }
-        }
-        else
-        {
-            nError = ReadSectors(pDrive, pByte, dwStartSector, 1);
-        }
-    }
-
-    MMCFree();
-
-    return(nError);
-} /* MMCReadSectors */
-
-#if (MMC_SUPPORT_WRITE == 1)
-/************************************************************/
-/*  MMCWriteSectors                                         */
-/************************************************************/
-int MMCWriteSectors(BYTE   bDevice,      void *pData,
-                    DWORD dwStartSector, WORD  wSectorCount)
-{
-    int    nError;
-    WORD   wWriteCount;
-    DRIVE *pDrive = 0;
-    BYTE  *pByte;
-
-    nError = MMC_OK;
-
-    MMCLock();
-
-    if (bDevice >= MMC_MAX_SUPPORTED_DEVICE)
-    {
-        nError = MMC_DRIVE_NOT_FOUND;
-    }
-    else
-    {
-        pDrive = &sDrive[bDevice];
-
-        if ((dwStartSector + wSectorCount) > pDrive->dTotalSectors)
-        {
-            nError = MMC_PARAM_ERROR;
-        }
-        if ((pDrive->wFlags & MMC_READY) == 0)
-        {
-            nError = MMC_DRIVE_NOT_FOUND;
-        }
-        if (pDrive->wFlags & MMC_READ_ONLY)
-        {
-            nError = MMC_NOT_SUPPORTED;
-        }
-    }
-
-    if (nError == MMC_OK)
-    {
-        pByte = (BYTE *) pData;
-        while (wSectorCount > 0)
-        {
-
-            if (wSectorCount < 256)
-            {
-                wWriteCount = wSectorCount;
-            }
-            else
-            {
-                wWriteCount = 256;
-            }
-
-            nError = WriteSectors(pDrive, pByte, dwStartSector, wWriteCount);
-            if (nError != MMC_OK)
-            {
-                break;
-            }
-
-            dwStartSector += wWriteCount;
-            wSectorCount  -= wWriteCount;
-            pByte         += (wWriteCount * MMC_SECTOR_SIZE);
-        }
-    }
-
-    MMCFree();
-
-    return(nError);
-} /* MMCWriteSectors */
-#endif
-
-
-
-

+ 0 - 100
mmcdrv.h

@@ -1,100 +0,0 @@
-/****************************************************************************
-*  This file is part of the MMC device driver.
-*
-*  Copyright (c) 2002-2004 by Michael Fischer. All rights reserved.
-*
-*  Redistribution and use in source and binary forms, with or without 
-*  modification, are permitted provided that the following conditions 
-*  are met:
-*  
-*  1. Redistributions of source code must retain the above copyright 
-*     notice, this list of conditions and the following disclaimer.
-*  2. Redistributions in binary form must reproduce the above copyright
-*     notice, this list of conditions and the following disclaimer in the 
-*     documentation and/or other materials provided with the distribution.
-*  3. Neither the name of the author nor the names of its contributors may 
-*     be used to endorse or promote products derived from this software 
-*     without specific prior written permission.
-*
-*  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 
-*  "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 
-*  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS 
-*  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL 
-*  THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, 
-*  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, 
-*  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS 
-*  OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED 
-*  AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, 
-*  OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF 
-*  THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 
-*  SUCH DAMAGE.
-*
-****************************************************************************
-*  History:
-*
-*  10.10.04  mifi   First Version
-****************************************************************************/
-#ifndef __MMCDRV_H__
-#define __MMCDRV_H__
-
-#include "typedefs.h"
-
-/*-------------------------------------------------------------------------*/
-/* global defines                                                          */
-/*-------------------------------------------------------------------------*/
-//
-// Here we can switch on/off some
-// feature of the software
-//
-#define MMC_SUPPORT_WRITE               1
-
-#define MMC_OK                          0x00
-#define MMC_ERROR                       0x01
-#define MMC_DRIVE_NOT_FOUND             0x02
-#define MMC_PARAM_ERROR                 0x03
-#define MMC_BUSY                        0x04
-#define MMC_NOT_SUPPORTED               0x08
-
-#define MMC_DRIVE_C                     0
-
-//
-// Sector size
-//
-#define MMC_SECTOR_SIZE                 512
-#define MAX_SECTOR_SIZE                 MMC_SECTOR_SIZE
-
-/*-------------------------------------------------------------------------*/
-/* global types                                                            */
-/*-------------------------------------------------------------------------*/
-typedef void MMC_MOUNT_FUNC(int nDevice);
-
-/*-------------------------------------------------------------------------*/
-/* global macros                                                           */
-/*-------------------------------------------------------------------------*/
-
-/*-------------------------------------------------------------------------*/
-/* Prototypes                                                              */
-/*-------------------------------------------------------------------------*/
-int MMCInit(int nMMCMode, MMC_MOUNT_FUNC * pMountFunc, MMC_MOUNT_FUNC * pUnMountFunc);
-
-int MMCMountAllDevices(int nMMCMode, BYTE *pSectorBuffer);
-
-int MMCGetSectorSize(BYTE bDevice);
-
-int MMCIsCDROMDevice(BYTE bDevice);
-
-int MMCIsZIPDevice(BYTE bDevice);
-
-int MMCUnMountDevice(BYTE bDevice);
-
-DWORD MMCGetTotalSectors(BYTE bDevice);
-
-int MMCReadSectors(BYTE bDevice, void *pData, DWORD dwStartSector, WORD wSectorCount);
-
-#if (MMC_SUPPORT_WRITE == 1)
-
-int MMCWriteSectors(BYTE bDevice, void *pData, DWORD dwStartSector, WORD wSectorCount);
-
-#endif
-
-#endif /* !__MMCDRV_H__ */

+ 332 - 0
mp3stream.c

@@ -0,0 +1,332 @@
+//
+// Created by Jordy Sipkema on 28/03/16.
+//
+
+#include "mp3stream.h"
+
+#include <arpa/inet.h>
+#include <sys/bankmem.h>
+#include <sys/heap.h>
+#include <sys/thread.h>
+#include <sys/timer.h>
+
+#include "vs10xx.h"
+
+#define OK              1
+#define NOK             0
+#define DEFAULT_VOLUME  7
+#define MSIZE           1024
+#define NUTSEGBUFFER    4096
+
+typedef struct _StreamArgs {
+    FILE *stream;
+} TStreamArgs;
+
+// Prototypes - Functions for internal use only! (They wont be visible outside this file!)
+THREAD(Mp3Player, args);
+void stopMp3PlayerThread(void);
+int ProcessStreamMetaData(FILE *stream);
+
+// Variables
+static bool stream_isplaying = false;
+static bool stream_connected = false;
+static bool stream_stopped = false;
+
+static u_char VS_volume = DEFAULT_VOLUME; //[0-16]; (Default volume = 7/16
+static u_long metaInt = 0;
+
+FILE *stream;
+TCPSOCKET *socket;
+
+bool connectToStream(char *ipaddr, u_short port, char *radioUrl)
+{
+    if (stream_connected == true)
+        return false;
+
+    stream_connected = false;
+    bool result = true;
+    char* data;
+
+    socket = NutTcpCreateSocket();
+    printf("Connecting to %s:%d%s\r\n", ipaddr, port, radioUrl);
+    if (NutTcpConnect(socket, inet_addr(ipaddr), port))
+    {
+        // An error has occurred.
+        printf("ConnectToStream: Error creating tcp socket.\n");
+        NutSleep(5000);
+        result = false;
+        return result;
+    }
+
+    stream = _fdopen((int)socket, "r+b");
+
+    fprintf(stream, "GET %s HTTP/1.0\r\n", radioUrl);
+    fprintf(stream, "Host: %s\r\n", ipaddr);
+    fprintf(stream, "User-Agent: Ethernut\r\n");
+    fprintf(stream, "Accept: */*\r\n");
+    fprintf(stream, "Icy-MetaData: 1\r\n");
+    fprintf(stream, "Connection: close\r\n\r\n");
+    fflush(stream);
+
+    // Server will respond with a HTTP-header. Fetch it to the buffer.
+    stream_connected = true;
+    stream_stopped = false;
+
+    data = (char *)malloc(MSIZE * sizeof(char));
+
+    while (fgets(data, MSIZE, stream))
+    {
+        /*
+         * Chop off the carriage return at the end of the line. If none
+         * was found, then this line was probably too large for our buffer.
+         */
+        char *cp = strchr(data, '\r');
+        if (cp == 0) continue;             // Input buffer overflow.
+
+        *cp = 0;
+
+        /*
+         * The header is terminated by an empty line.
+         */
+        if (*data == 0) break;
+
+        if (strncmp(data, "icy-metaint:", 12) == 0)
+            metaInt = atol(data + 12);
+        printf("%s\n", data);
+    }
+
+    free(data);
+
+    return result;
+}
+
+bool play()
+{
+    if (stream_connected == false)
+        return false;
+
+    if (stream_isplaying == true)
+        return false;
+
+    // else:
+    stream_isplaying == true;
+
+    TStreamArgs *streamArgs = &(TStreamArgs){
+            .stream = stream,
+            //.metaint = metaInt
+    };
+
+    NutThreadCreate("Mp3Player", Mp3Player, streamArgs, 512);
+    printf("Mp3Player thread created. Device should start playing the stream.\n");
+
+    return true;
+}
+
+u_char volumeUp(void)
+{
+    if (VS_volume >= 16)
+        return VS_volume;
+
+    //else:
+    ++VS_volume;
+    VS_volume = VS_volume % 17;
+    setVolume();
+
+    return VS_volume;
+}
+
+u_char volumeDown(void)
+{
+    if (VS_volume <= 0)
+        return VS_volume;
+
+    //else:
+    --VS_volume;
+    VS_volume = VS_volume % 17;
+    setVolume();
+
+    return VS_volume;
+}
+
+void setVolume(void){
+    u_char volumeToSet = (128 - (VS_volume * 8)) % 129;
+    VsSetVolume(volumeToSet, volumeToSet);
+    printf("- VS_volume level: %d/16\n", VS_volume);
+}
+
+void killPlayerThread(void)
+{
+    printf("Signal to stop the stream sent.\n");
+    stream_stopped = true;
+}
+
+THREAD(Mp3Player, args)
+//void function(void* args) //TODO: REMOVE THIS, THIS IS ONLY TO TRICK CLION!
+{
+    // Unpack the args passed to the thread initializer.
+    TStreamArgs *streamArgs = (TStreamArgs *)args;
+    FILE *stream = streamArgs->stream;
+
+    int result = NOK;
+
+    size_t rbytes = 0;
+    char *mp3buf;
+    u_char ief;
+    int got = 0;
+    u_long mp3left = metaInt;
+
+    // Init MP3-buffer. NutSegBuf is a global system buffer.
+    if (0 != NutSegBufInit(NUTSEGBUFFER)){
+        // Reset the global buffer.
+        ief = VsPlayerInterrupts(0);
+        NutSegBufReset();
+        VsPlayerInterrupts(ief);
+
+        result = OK;
+    }
+
+    // Init the VS1003b hardware.
+    if (result == OK){
+        if (-1 == VsPlayerInit()) {
+            if (-1 == VsPlayerReset(0)){
+                result = NOK;
+            }
+        }
+    }
+
+    // Set the volume to the correct level
+    setVolume();
+
+    for(;;)
+    {
+        /*
+         * Query the number of bytes available in the MP3 buffer.
+         */
+        ief = VsPlayerInterrupts(0);
+        mp3buf = NutSegBufWriteRequest(&rbytes);
+        VsPlayerInterrupts(ief);
+
+        /*
+         * If the player is not running, kick it.
+         * This should only occur once.
+         */
+        if (VsGetStatus() != VS_STATUS_RUNNING) {
+            puts("Player not running.");
+            if (rbytes < 1024){
+                puts("Kick player in 3 2 1..:");
+                VsPlayerKick();
+            }
+        }
+
+
+
+        /*
+         * Do not read pass metadata.
+         * This causes ugly hiccups.
+         */
+        if (metaInt && rbytes > mp3left){
+            rbytes = mp3left;
+        }
+
+        /*
+         * Read directly into the MP3 buffer.
+         */
+        while (rbytes) {
+            if (stream_stopped == true) {
+                stopMp3PlayerThread();
+            }
+
+            if ((got = fread(mp3buf, 1, rbytes, stream)) > 0) {
+                ief = VsPlayerInterrupts(0);
+                mp3buf = NutSegBufWriteCommit(got);
+                VsPlayerInterrupts(ief);
+
+                if (metaInt) {
+                    mp3left -= got;
+                    if (mp3left == 0) {
+                        ProcessStreamMetaData(stream);
+                        mp3left = metaInt;
+                    }
+                }
+
+                if (got < rbytes && got < 512) {
+                    printf("%lu buffered\n", NutSegBufUsed());
+                    NutSleep(250);
+                }
+                else {
+                    NutThreadYield();
+                }
+            } else {
+                break;
+            }
+            rbytes -= got;
+        }
+
+        if (got <= 0) break;
+
+
+    } // end for(;;)
+
+    while (NutSegBufUsed() > 10){
+        NutSleep(250);
+    }
+
+    stopMp3PlayerThread();
+}
+
+void stopMp3PlayerThread(void)
+{
+    printf("Signal to stop the stream recieved\n.");
+    stream_connected = false;
+    stream_isplaying = false;
+    VsPlayerStop();
+    NutTcpCloseSocket(socket);
+    NutThreadExit();
+}
+
+int ProcessStreamMetaData(FILE *stream)
+{
+    u_char blks = 0;
+    u_short cnt;
+    int got;
+    int rc = 0;
+    u_char *mbuf;
+
+    /*
+     * Wait for the lenght byte.
+     */
+    got = fread(&blks, 1, 1, stream);
+    if(got != 1) {
+        return -1;
+    }
+    if (blks) {
+        if (blks > 32) {
+            printf("Error: Metadata too large, %u blocks\n", blks);
+            return -1;
+        }
+
+        cnt = blks * 16;
+        if ((mbuf = malloc(cnt + 1)) == 0) {
+            printf("Can't malloc memory for metadata parsing\n");
+            return -1;
+        }
+
+        /*
+         * Receive the metadata block.
+         */
+        for (;;) {
+            if ((got = fread(mbuf + rc, 1, cnt, stream)) <= 0) {
+                return -1;
+            }
+            if ((cnt -= got) == 0) {
+                break;
+            }
+            rc += got;
+            mbuf[rc] = 0;
+        }
+
+        printf("\nMeta='%s'\n", mbuf);
+        free(mbuf);
+    }
+    return 0;
+}

+ 25 - 0
mp3stream.h

@@ -0,0 +1,25 @@
+//
+// Created by Jordy Sipkema on 28/03/16.
+//
+
+#ifndef MUTLI_OS_BUILD_MP3STREAM_H
+#define MUTLI_OS_BUILD_MP3STREAM_H
+
+#include "typedefs.h"
+
+#include <netinet/tcp.h>
+#include <sys/socket.h>
+
+#include <stdio.h>
+#include <string.h>
+
+bool play(void);
+bool connectToStream(char* ipaddr, u_short port, char *radioUrl);
+void killPlayerThread(void);
+
+u_char volumeUp(void);
+u_char volumeDown(void);
+void setVolume(void); // Do not use this one, this is invoked by volumeUp/Down
+
+
+#endif //MUTLI_OS_BUILD_MP3STREAM_H

+ 7 - 10
network.c

@@ -58,7 +58,7 @@ void httpGet(char address[], void (*parser)(char*)){
     TCPSOCKET* sock = NutTcpCreateSocket();
 
     char buffer[2];
-    char* content = (char*) calloc(1 , 800);
+    char* content = (char*) malloc(900);
     char enters = 0;
     int t = 0;
 
@@ -67,7 +67,7 @@ void httpGet(char address[], void (*parser)(char*)){
     }else if (NutTcpConnect(sock, inet_addr("62.195.226.247"), 80)) {
         printf("Can't connect to server\n");
     }else if (NutTcpSetSockOpt(sock, SO_RCVTIMEO, &rx_to, sizeof(rx_to))){
-
+        printf("Can't set sock options\n");
     }else{
         FILE *stream;
         stream = _fdopen((int) sock, "r+b");
@@ -77,7 +77,6 @@ void httpGet(char address[], void (*parser)(char*)){
         fflush(stream);
 
         printf("Headers writed. Now reading.");
-        NutDelay(500);
         //Removing header:
         while(fgets(buffer, sizeof(buffer), stream) != NULL) {
             if(enters == 4) {
@@ -93,16 +92,14 @@ void httpGet(char address[], void (*parser)(char*)){
             }
         }
         fclose(stream);
+
+        content[t] = '\0';
+        printf("\nContent size: %d, Content: %s \n", t, content);
+        parser(content);
+        free(content);
     }
     NutTcpCloseSocket(sock);
-
-    content[t] = '\0';
-    printf("\nContent size: %d, Content: %s \n", t, content);
-    parser(content);
-    free(content);
-
     isReceiving = false;
-    return content;
 }
 
 bool NetworkIsReceiving(void){

+ 7 - 1
ntp.c

@@ -104,6 +104,7 @@ void NtpSync(void){
     /* Ophalen van pool.ntp.org */
     isSyncing = true;
     httpGet("/gettimezone.php", parsetimezone);
+    _daylight = 0;
     printf(TIME_ZONE);
     NutDelay(100);
     //puts("Tijd ophalen van pool.ntp.org (213.154.229.24)");
@@ -144,5 +145,10 @@ void NtpWriteTimeToEeprom(tm time_struct){
 }
 
 void setTimeZone(int timezone){
-    _timezone = -timezone * 3600;
+    TIME_ZONE = timezone;
+    _timezone = -1*timezone * 3600;
+}
+
+int getTimeZone(){
+    return TIME_ZONE;
 }

+ 4 - 1
ntp.h

@@ -5,7 +5,7 @@
 #ifndef _Ntp_H
 #define _Ntp_H
 
-typedef enum {false, true} bool;
+#include "typedefs.h"
 
 extern bool NtpIsSyncing(void);
 extern void NtpInit(void);
@@ -16,4 +16,7 @@ extern bool NtpTimeIsValid(void);
 void NtpCheckValidTime(void);
 void NtpWriteTimeToEeprom(tm);
 bool NtpCompareTime(tm, tm);
+
+void setTimeZone(int timezone);
+int getTimeZone();
 #endif /* _Ntp_H */

+ 0 - 151
remcon.c

@@ -1,151 +0,0 @@
-/*! \file
- * remcon.c contains all interface- and low-level routines that
- * perform handling of the infrared bitstream
- * [COPYRIGHT]  Copyright (C) STREAMIT BV
- *  \version 1.0
- *  \date 26 september 2003
- */
-
-
-
-#define LOG_MODULE  LOG_REMCON_MODULE
-
-#include <stdlib.h>
-#include <fs/typedefs.h>
-#include <sys/heap.h>
-
-#include <sys/event.h>
-#include <sys/atom.h>
-#include <sys/types.h>
-#include <dev/irqreg.h>
-
-#include "system.h"
-#include "portio.h"
-#include "remcon.h"
-#include "display.h"
-#include "keyboard.h"
-#include "led.h"
-
-
-/*-------------------------------------------------------------------------*/
-/* local variable definitions                                              */
-/*-------------------------------------------------------------------------*/
-static HANDLE  hRCEvent;
-
-/*-------------------------------------------------------------------------*/
-/* local routines (prototyping)                                            */
-/*-------------------------------------------------------------------------*/
-static void RcInterrupt(void*);
-static void RcClearEvent(HANDLE*);
-
-
-/*!
- * \addtogroup RemoteControl
- */
-
-/*@{*/
-
-/*-------------------------------------------------------------------------*/
-/*                         start of code                                   */
-/*-------------------------------------------------------------------------*/
-
-
-
-/* ÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍ */
-/*!
- * \brief ISR Remote Control Interrupt (ISR called by Nut/OS)
- *
- *  NEC-code consists of 5 parts:
- *
- *  - leader (9 msec high, 4,5 msec low)
- *  - address (8 bits)
- *  - inverted address (8 bits)
- *  - data (8 bits)
- *  - inverted data (8 bits)
- *
- *  The first sequence contains these 5 parts, next
- *  sequences only contain the leader + 1 '0' bit as long
- *  as the user holds down the button
- *  repetition time is 108 msec in that case
- *
- *  Resolution of the 16-bit timer we use here is 4,3 usec
- *
- *  13,5 msecs are 3109 ticks
- *  '0' is 1,25 msecs (260 ticks)
- *  '1' is 2,25 msecs (517 ticks)
- *
- * \param *p not used (might be used to pass parms from the ISR)
- */
-/* ÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍ */
-static void RcInterrupt(void *p)
-{
-	// Hier ISR implementeren voor bijv. NEC protocol
-}
-
-/* ÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍ */
-/*!
- * \brief Clear the eventbuffer of this module
- *
- * This routine is called during module initialization.
- *
- * \param *pEvent pointer to the event queue
- */
-/* ÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍ */
-static void RcClearEvent(HANDLE *pEvent)
-{
-    NutEnterCritical();
-
-    *pEvent = 0;
-
-    NutExitCritical();
-}
-
-
-
-/* ÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍ */
-/*!
- * \brief Initialise the Remote Control module
- *
- * - register the ISR in NutOS
- * - initialise the HW-timer that is used for this module (Timer1)
- * - initialise the external interrupt that inputs the infrared data
- * - flush the remote control buffer
- * - flush the eventqueue for this module
- */
-/* ÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍ */
-void RcInit()
-{
-    int nError = 0;
-
-    EICRB &= ~RC_INT_SENS_MASK;    // clear b0, b1 of EICRB
-
-    // Install Remote Control interrupt
-    nError = NutRegisterIrqHandler(&sig_INTERRUPT4, RcInterrupt, NULL);
-    if (nError == FALSE)
-    {
-/*
- *  ToDo: control External Interrupt following NutOS calls
-#if (NUTOS_VERSION >= 421)
-        NutIrqSetMode(&sig_INTERRUPT4, NUT_IRQMODE_FALLINGEDGE);
-#else
-        EICRB |= RC_INT_FALLING_EDGE;
-#endif
-        EIMSK |= 1<<IRQ_INT4;         // enable interrupt
- */
-        EICRB |= RC_INT_FALLING_EDGE;
-        EIMSK |= 1<<IRQ_INT4;         // enable interrupt
-    }
-
-    // Initialise 16-bit Timer (Timer1)
-    TCCR1B |= (1<<CS11) | (1<<CS10); // clockdivider = 64
-    TIFR   |= 1<<ICF1;
-    //TIMSK = 1<<TICIE1;
-
-    RcClearEvent(&hRCEvent);
-
-
-}
-
-/* ---------- end of module ------------------------------------------------ */
-
-/*@}*/

+ 0 - 52
remcon.h

@@ -1,52 +0,0 @@
-/* ========================================================================
- * [PROJECT]    SIR
- * [MODULE]     Remote Control
- * [TITLE]      remote control header file
- * [FILE]       remcon.h
- * [VSN]        1.0
- * [CREATED]    1 july 2003
- * [LASTCHNGD]  1 july 2003
- * [COPYRIGHT]  Copyright (C) STREAMIT BV 2010
- * [PURPOSE]    remote control routines for SIR
- * ======================================================================== */
-
-/*-------------------------------------------------------------------------*/
-/* global defines                                                          */
-/*-------------------------------------------------------------------------*/
-#define RC_OK                 0x00
-#define RC_ERROR              0x01
-#define RC_BUSY               0x04
-
-#define RCST_IDLE             0x00
-#define RCST_WAITFORLEADER    0x01
-#define RCST_SCANADDRESS      0x02
-#define RCST_SCANDATA         0x03
-
-#define RC_INT_SENS_MASK      0x03
-#define RC_INT_FALLING_EDGE   0x02
-#define RC_INT_RISING_EDGE    0x03
-
-#define IR_RECEIVE            4
-#define IR_BUFFER_SIZE        1
-
-
-/*-------------------------------------------------------------------------*/
-/* export global routines (interface)                                      */
-/*-------------------------------------------------------------------------*/
-void    RcInit(void);
-
-
-/*  ÍÍÍÍ  End Of File  ÍÍÍÍÍÍÍÍ ÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍÍ */
-
-
-
-
-
-
-
-
-
-
-
-
-

+ 26 - 0
typedefs.h

@@ -12,6 +12,22 @@
  * [PURPOSE]    global typedefs
  * ======================================================================== */
 
+/*
+ *  Copyright 20152016-TI2.3a6, 2016.
+ *
+ *  Project             : 20152016-TI2.3a6-Internet Radio
+ *  Module              : Type definitions
+ *  File name           : Typedefs.h
+ *  Revision            : 1.1
+ *  Creation Date       : 2016/03/04
+ *
+ *  Description         : Global type definitions for the SIR100/120
+ *                        firmware.
+ *
+ *  Changelog       1.1 : Add type definitions for TI2.3a6 software.
+ *                        - Add bool
+ */
+
 
 /*--------------------------------------------------------------------------*/
 /*  Include files                                                           */
@@ -29,6 +45,16 @@
 /*     Make sure that any modification made to this table are reflected by  */
 /*     the LcdErrorStirngs table! (an error is bad but showing the wrong    */
 /*     error is too much....) */
+
+// Additions based on version 1.1
+
+typedef enum {false, true} bool;
+
+
+
+
+
+
 typedef enum _TERRORCODE
 {
     OK = 0,                             /* All ok */

+ 1 - 1
vs10xx.c

@@ -505,7 +505,7 @@ int VsPlayerKick(void)
          *  for the VS1003 we need an extra reset
          *  here before we start playing a stream...
          */
-        VsPlayerSetMode(VS_SM_RESET);
+//        VsPlayerSetMode(VS_SM_RESET);
 //        NutDelay(10);
 //        LogMsg_P(LOG_DEBUG,PSTR("Kick: CLOCKF = [0x%02X]"),VsRegRead(VS_CLOCKF_REG));
 //        LogMsg_P(LOG_DEBUG,PSTR("Kick: CLOCKF = [0x%02X]"),VsRegRead(VS_CLOCKF_REG));