VS1005 MP3 Player with USB Host

Installing and using VSIDE tools for VLSI Solution's devices that contain a VSDSP signal processor.
Srikanth
User
Posts: 10
Joined: Thu 2016-08-18 9:03

VS1005 MP3 Player with USB Host

Post by Srikanth »

Hello all,

I am very much new to VLSI products, I downloaded and installed VSIDE. My application requirement is
1) Play mp3 files from USB.
2) Fast forward / Rewind/ Next Track/ Previous Track/ Pause / Play with help of hardware buttons. I am not using LCD in my application.
3) FM

the model overview of VS1005 says that it supports USB Host, inbuilt headphone amplifier and internal mp3 decoder and FM section.

I am confused about where to start with and how to start.

When I create a project from VSIDE It says me to select
1) VS1005 Legacy VSOS application
2) VS1005 solution
3) VS1005 VSOS3 application

I don't know which one I have to select and which option suits the best for my requirement.

I have few more queries regarding my custom application
1) Can we program VS1005 as standalone application without VSOS i.e. like most of the single threaded microcontroller programs?
2) Do we need to have kernel to configure VS1005 as USB Host and to have kernel do we need VSOS.
3) Simple MP3 Player implemented in the example code, it plays file from storage device i.e. from SD Card.
To play MP3 file from a USB Device, do our code need to reside in USB. I mean is it mandatory for the application code to be in USB and run from USB to read files in USB disk.

I searched the forum for the related topic and couldn't find one related to my application. So I posted it here.
If possible please post necessary links in your reply.

Thanks,
Srikanth
User avatar
Panu
VSDSP Expert
Posts: 2829
Joined: Tue 2010-06-22 13:43

Re: VS1005 MP3 Player with USB Host

Post by Panu »

Dear Srikanth,
many thanks for your message and welcome to the forum!

These are all very good questions, and a proper answer should be quite long. But if it's all right with you, I'll quickly write some short answers to get you started. You can ask further questions then.
I am very much new to VLSI products, I downloaded and installed VSIDE.
That's great! You're on the right track!
My application requirement is
1) Play mp3 files from USB. 2) Fast forward / Rewind/ Next Track/ Previous Track/ Pause / Play 3) FM [...] with help of hardware buttons. I am not using LCD in my application.
That's reasonable and we have a lot of example solutions that do almost what you need. And as a matter of a fact, I'm working on a new player solution which would be even more useful for you.

Basically you have two options:

1) use a microcontroller with UART to control the VS1005 that is running the VSOS Shell. Use the UART to enter commands such as CD, DIR, PLAYFILE and PLAYDIR to switch to different storage devices, optionally list files and run music player programs. Image
If you take this route, you might not need to write any VS1005 code at all, only use our existing programs via the UART.

Or 2) write a top-level program that runs the player programs and/or calls the decoder libraries directly.Image
I remeber that you don't want to use LCD. But the logic to handle the buttons and the player could be taken from the Classic Player example and as said, I'm working on a new example that will be using mechanical buttons.
1) Can we program VS1005 as standalone application without VSOS i.e. like most of the single threaded microcontroller programs?
Yes, of course, but that would be a lot more difficult and involves a lot more learning than writing simple VSOS programs. With VSOS, we've already done the work of handling SD cards, USB sticks, reading and writing files, even playing music. You can just fopen() a file, read and write, just like in any normal "C" type (#include <stdio.h>) environment.

In VSOS, you can play a file by running a ready-made program with a single line, for example: RunProgram("PLAYFILE","D:SONG.WMA");.

Furthermore, while all of the above is released as source code, so you could theoretically take the source code and compile it into one massive statically linked application that boots directly from the flash, there is one notable exception: our most valued intellectual property: the audio decoders. These are offered only in binary form: as VSOS loadable libraries. For licensing reasons MP3 is included on the chip ROM. But all other decoders are loaded into on-chip RAM at runtime by the VSOS.

So using VSOS is your only practical solution, but don't worry, it's quite easy; in any case much easier that learning our raw hardware.
2) Do we need to have kernel to configure VS1005 as USB Host and to have kernel do we need VSOS.
You need the kernel. To use a USB flash, you can place the line "USBHOST U" into CONFIG.TXT to activate the USB flash as drive U at boot time. Or if you want to save memory, you can load and unload the USB driver as needed.
To play MP3 file from a USB Device, do our code need to reside in USB. I mean is it mandatory for the application code to be in USB and run from USB to read files in USB disk.
No no, typically VSOS application code (programs and libraries) are loaded and run from SPI flash, but they can be loaded and run from any storage medium, such as SD card or USB flash. This is especially useful for doing firmware updates.

Please think about this for a while and ask more questions!

-Panu
Srikanth
User
Posts: 10
Joined: Thu 2016-08-18 9:03

Re: VS1005 MP3 Player with USB Host

Post by Srikanth »

Hello VLSI Team,

with reference to the document visde user manual named -> "vside_um.pdf".

In section 2.3
Heading : License manager server installation
It says
VSIDE needs a connection to VSIDE license manager server. To set up the license manager,
download the separate VSIDE license manager package and install it according to its instructions
delivered with the package.


I didn't find any separate VSIDE license manager link in the download link provided on your web page.
as the above statement says "download the separate VSIDE license manager package" which I presume that it is another file apart from VSIDE installation package.

can you please forward the link do download VSIDE license manager installation package.
I searched in the forum as well but didn't find any links.

moreover I can't enter into debug mode as explained in the section 3.5.
"3.5 Executing and debugging the code" from the same referred document.

I am getting the below error for the project that is provided in this forum as sample codes VSOS_330a_RootAndLibrariesSourceCode/solutions/PlayFiles/PlayFiles.solution :
-----------------------------------------------------------------
Loading system 'C:/VSIDE/plugins/simulator.system'...
Loading 'Emulation-Debug/MyProject.coff'...
Error: could not load executable!
-------------------------------------------------------------------

With the above error I understood that I can't find the file MyProject.coff in the specified directory.

If i build the code, everything is fine. No errors. This is the output window while building.

--------------------------------------------------------------------------------------------------
Build started. Project: PlayFiles, configuration: Emulation-Debug

lcc -g -hhw_desc -O6 -fsmall-code -DDEBUG -Iinclude -IC:\VSIDE\libvs1005g_vsos3 -o Emulation-Debug\main.o C:\Users\Srikanth\Downloads\root\ and\ library\ sourcecode\VSOS_330a_RootAndLibrariesSourceCode\solutions\PlayFiles\main.c

optimizing (459): 358 350.350.349.349.349
Successfully compiled 6459 lines (146 in source) with 0 warnings.
C 349 CF 0 X 174 Y 0 F 0
voplinkg -k -m mem_desc_app02.mem C:\VSIDE/libvs1005g_vsos3/vsos03.o Emulation-Debug\main.o -o Emulation-Debug\MyProject.coff -L. -Llib -LC:\VSIDE\libvs1005g_vsos3 -lvsos03 -lc -lgeneral -lcodecmpgsmall -lrtossmall

Linkinfo: _appFlags is absolute 2255
Linkinfo: _currentDirectory is absolute 2254
Total words: I 475, X 431, Y 0.
copy loadable.app PlayFiles.dl3 /y
1 file(s) copied.

copy loadable.ap3 PlayFiles.dl3 /y
1 file(s) copied.
rem Remove both REMs to copy automatically to SD card
copy PlayFiles.dl3 \sys /y

1 file(s) copied.

Finished.
--------------------------------------------------------------------------------------------------------

I request VLSI team to guide me to overcome this issue and to provide the download link to VSIDE license manager package.

Thanks and regards,
Srikanth
User avatar
Panu
VSDSP Expert
Posts: 2829
Joined: Tue 2010-06-22 13:43

Re: VS1005 MP3 Player with USB Host

Post by Panu »

Hi!

Short answer:
Copy the executable file PlayFiles.dl3 to your board's flash using USB and run it from the command line. Or use the PlayFiles.dl3 already distributed in the VSOS root image. (root/sys/PlayFiles.dl3 - in your developer board this should be S:SYS/PlayFiles.dl3)

Long answer:
First of all, you don't need VSIDE to run PlayFiles. You can run it from the command line (VSOS Shell) using UART (HyperTerminal, Termite, PuTTY, TeraTerm etc). You only need VSIDE if you want to make modifications to the PlayFiles program. You may need to do something like press button S2 during boot to boot the developer board to the command line mode.

Ok, then to your question.

The VSIDE that you can load from our website doesn't need a license manager any more. The copy protection was removed from the public versions about 10 years ago.

VSOS executables, sadly, cannot be debugged using the UART. They need to be loaded by the operating system from flash or SD card etc. The VSIDE creates an executable program, in this case the file PlayFiles.dl3. You need to copy, or let VSIDE to copy, that executable to the developer board's flash, into the subfolder SYS. Then you can run the PlayFiles.DL3 by typing "PlayFiles" in the VSOS sell.

To get started, see all the videos at:
viewtopic.php?t=1273#p5655

-Panu
Srikanth
User
Posts: 10
Joined: Thu 2016-08-18 9:03

Re: VS1005 MP3 Player with USB Host

Post by Srikanth »

Hello VLSI Team,

Please excuse me for asking each and every single silly query striking my head.

This is the sample code that I have written to generate Interrupt Service Routine for GPIO0

This is hardware configuration file
hw_config.h

Code: Select all

================= hw_config.h ===========
#ifndef __HW_CONFIG__
#define __HW_CONFIG__

#define BUTTON_MP3_FM          					0x00			//GPIO0.0
#define BUTTON_PLAY_PAUSE 					0x01			//GPIO0.1
#define BUTTON_VOLUME_PLUS					0x02			//GPIO0.2
#define BUTTON_VOLUME_MINUS				0x03			//GPIO0.3
#define BUTTON_PREVIOUS_TRACK				0x04			//GPIO0.4
#define BUTTON_NEXT_TRACK					0x05			//GPIO0.5


#define BUTTON_MP3_FM_DEFAULT_VAL 			0	//GPIO0.0
#define BUTTON_PLAY_PAUSE_DEFAULT_VAL 		0	//GPIO0.1
#define BUTTON_VOLUME_PLUS_DEFAULT_VAL		0	//GPIO0.2
#define BUTTON_VOLUME_MINUS_DEFAULT_VAL		0	//GPIO0.3
#define BUTTON_PREVIOUS_TRACK_DEFAULT_VAL	0	//GPIO0.4
#define BUTTON_NEXT_TRACK_DEFAULT_VAL		0	//GPIO0.5

#endif
=======================================
GPIO driver files for my application
GPIO_Drv.h

Code: Select all

================= GPIO_Drv.h ===========
#ifndef __GPIO_DRV_H__
#define __GPIO_DRV_H__
#include <vo_stdio.h>
#include <stdlib.h>
#include <sysmemory.h>
#include <vsos.h>
#include <vs1005g.h>
#include <vo_gpio.h>
#include "hw_config.h"

#define PIN0 	0x0001
#define PIN1 	0x0002
#define PIN2 	0x0004
#define PIN3 	0x0008
#define PIN4 	0x0010
#define PIN5 	0x0020
#define PIN6 	0x0040
#define PIN7 	0x0080
#define PIN8 	0x0100
#define PIN9 	0x0200
#define PIN10 	0x0400
#define PIN11 	0x0800
#define PIN12 	0x1000
#define PIN13 	0x2000
#define PIN14 	0x4000
#define PIN15 	0x8000

typedef enum 
{
INPUT = 0,
OUTPUT = 1
}PIN_DIR;

typedef enum
{
LOW =0,
HIGH = ~LOW
}PIN_VAL;

auto void InitGPIO(void);


#endif
=======================================
GPIO_Drv.c

Code: Select all

================= GPIO_Drv.c ===========
#include "GPIO_Drv.h"
#include "MP3_Drv.h"

volatile static u_int16 GPIOFlag; // To read GPIO0 interrupt source pin for future use



#pragma interrupt_x INTV_GPIO0
void GPIO0_Interrupt(void)
{
	u_int16 flag=0;
	static u_int16 toggleflag = 0;
	u_int16 *ptr;
	ptr = (u_int16 *)INT_ORIGIN0;
	if((*ptr) & (INTV_GPIO0) == (INTV_GPIO0))
	{
		flag = *(u_int16 *)GPIO0_INT_PEND;
		if(flag & PIN0 == PIN0)
		{
			Source();
			GPIOFlag |= (1<<BUTTON_MP3_FM);
		}
		if(flag & PIN1 == PIN1)
		{
			if(toggleflag==0)
			{
				Pause();
				toggleflag=1;
			}
			else
			{
				Play();
				toggleflag=0;
			}
			GPIOFlag |= (1<<BUTTON_PLAY_PAUSE);
		}
		if(flag & PIN2 == PIN2)
		{
			VolumePlus();
			GPIOFlag |= (1<<BUTTON_VOLUME_PLUS);
		}
		if(flag & PIN3 == PIN3)
		{
			VolumeMinus();
			GPIOFlag |= (1<<BUTTON_VOLUME_MINUS);
		}
		if(flag & PIN4 == PIN4)
		{
			PreviousTrack();
			GPIOFlag |= (1<<BUTTON_PREVIOUS_TRACK);
		}
		if(flag & PIN5 == PIN5)
		{
			NextTrack();
			GPIOFlag |= (1<<BUTTON_NEXT_TRACK);
		}
		if(flag & PIN6 == PIN6)
		{
			//Not implemented
		}
		if(flag & PIN7 == PIN7)
		{
			//Not implemented		
		}
		if(flag & PIN8 == PIN8)
		{
			//Not implemented		
		}
		if(flag & PIN9 == PIN9)
		{
			//Not implemented		
		}
		if(flag & PIN10 == PIN10)
		{
			//Not implemented		
		}
		if(flag & PIN11 == PIN11)
		{
			//Not implemented		
		}
		if(flag & PIN12 == PIN12)
		{
			//Not implemented		
		}
		if(flag & PIN13 == PIN13)
		{
			//Not implemented		
		}
		if(flag & PIN14 == PIN14)
		{
			//Not implemented		
		}
		if(flag & PIN15 == PIN15)
		{
			//Not implemented		
		}
		flag = 0;
	}
	ptr = (u_int16 *)INT_GLOB_ENA;
	(*ptr)= 0;
}

auto void InitGPIO(void)
{
u_int16 *ptr;
GpioSetAsInput(BUTTON_MP3_FM);
GpioSetAsInput(BUTTON_PLAY_PAUSE);
GpioSetAsInput(BUTTON_VOLUME_PLUS);
GpioSetAsInput(BUTTON_VOLUME_MINUS);
GpioSetAsInput(BUTTON_PREVIOUS_TRACK);
GpioSetAsInput(BUTTON_NEXT_TRACK);
// Enabling Interrupts with priority 3 (high)
ptr = (u_int16 *)INT_ENABLE0_HP;
(*ptr) |= (0x00FF & (1<<INTV_GPIO0));
ptr = (u_int16 *)INT_ENABLE0_LP;
(*ptr) |= (0x00FF & (1<<INTV_GPIO0));
// Clearing Interrupt Enable Counter register if it is non zero
ptr = (u_int16 *)INT_ENCOUNT;
if((*ptr) & 0x0007 !=0)
{
	ptr = (u_int16 *)INT_GLOB_ENA;
	(*ptr) = 0;
}
	
	
}
=======================================
Requirement : I want to process the interrupt using Interrupt service routines and not using polling way. GPIO0 has the hardware buttons and application must trigger interrupt when there is change of level.
I have another doubt. Is there any register that sets the falling edge or rising edge to trigger interrupt on GPIO Pins.
Is this the correct way of calling Interrupt Service Routines in VSIDE.

Please correct my code if I am wrong anywhere.
I didn't find any code example explaining about the way to initialize the registers to process Interrupt service routines.

Thanks
Srikanth
User avatar
Henrik
VLSI Staff
Posts: 1294
Joined: Tue 2010-06-22 14:10

Re: VS1005 MP3 Player with USB Host

Post by Henrik »

Hello Srikanth!

I am looking into your question and will answer to it shortly.

Kind regards,
- Henrik
Good signatures never die. They just fade away.
User avatar
Panu
VSDSP Expert
Posts: 2829
Joined: Tue 2010-06-22 13:43

Re: VS1005 MP3 Player with USB Host

Post by Panu »

#pragma interrupt_x INTV_GPIO0
#pragmas are not processed by the C preprosessor, you need to give the vector as plain integer.

Also, VS1005 interrupt hardware is in Y space, not X, so you need to use #pragma interrupt_y 0x27 to declare GPIO0 interrupt in VS1005.

Henrik will probably add some useful remarks regarding setting the vector manually, as we've noticed that the automatic vectoring isn't 100% reliable :|

-Panu
User avatar
Henrik
VLSI Staff
Posts: 1294
Joined: Tue 2010-06-22 14:10

Re: VS1005 MP3 Player with USB Host

Post by Henrik »

Hello again!

You have lots of good thought in your code, but there are certain points which will prevent it from working.

As a point of reference, I made a very simple code example that reads buttons from GPIO0_0 through GPIO0_3 using an interrupt, then handle those button presses in a main program.

The reason for doing it this way is to keep the interrupt as short as possible. Long interrupts sooner or later cause trouble with real-time features, like glitches in audio playback or e.g. SPI communications (if an application has such features). This is here avoided by using a very short interrupt to collect the data, but to handle these events in a main program that doesn't have strict real-time requirements.

From the example you will also see other recommended stylistical habits, like using the PERIP() macro, which makes peripheral accesses easier to read.

Code: Select all

#include <vo_stdio.h>
#include <volink.h>     // Linker directives like DLLENTRY
#include <apploader.h>  // RunLibraryFunction etc
#include <timers.h>
#include <consolestate.h>
#include <string.h>
#include <vs1005g.h>
#include <vo_gpio.h>

u_int16 gpioState=0, gpioPend=0;

#pragma interrupt y 0x27
void Gpio0Interrupt(void) {
  /* Let's make the interrupt as short as possible. */
  gpioPend |= PERIP(GPIO0_INT_PEND); /* Get which bits have changed. */
  PERIP(GPIO0_INT_PEND) = 0xFFFF;    /* Clear the flags. */
  gpioState = PERIP(GPIO0_IDATA);    /* Get the actual GPIO data. */
}

ioresult main(char *parameters) {
  int quit = 0;

  if (!strcmp(parameters, "-h")) {
    printf("Usage: GpioDemo [-h]\n");
    goto finally;
  }

  /* Make GPIO0_0 through GPIO0_3 inputs */
  GpioSetAsInput(0x00);
  GpioSetAsInput(0x01);
  GpioSetAsInput(0x02);
  GpioSetAsInput(0x03);

  /* We are interested in the rising edges of GPIO0_0 through GPIO0_3... */
  PERIP(GPIO0_INT_RISE) = 0x000F;
  /* ... as well as the falling edges. */
  PERIP(GPIO0_INT_FALL) = 0x000F;

  /* Activate GPIO0 interrupt at lowest interrupt priority */
  PERIP(INT_ENABLE0_LP) |= INTF_GPIO0;
  PERIP(INT_ENABLE0_HP) &= ~INTF_GPIO0;
  
  /* Run main loop until Ctrl-C is pushed. */
  while (!(appFlags & APP_FLAG_QUIT)) {
    u_int16 localGpioPend, localGpioState;

    /* Disable interrupts */
    Disable();
    /* Take local copy of the variables */
    localGpioPend = gpioPend;
    localGpioState = gpioState;
    /* Clear main variables. */
    gpioPend = 0;
    /* Re-enable interrupts */
    Enable();

    if (localGpioPend) {
      int i;
      for (i=0; i<4; i++) {
	if ((localGpioPend >> i) & 1) {
	  printf("GPIO0_%d = %d\n", i, (localGpioState>>i) & 1);
	}
      }
    } else {
      /* Wait for one millisecond */
      Delay(1);
    }
  }

  /* Remove the interrupt */
  PERIP(INT_ENABLE0_LP) &= ~INTF_GPIO0;
  printf("End.\n");

 finally:
  return S_OK;
}
For your convenience, the demonstration Solution is attached below.

Kind regards,
- Henrik
Attachments
GpioDemo.zip
Demo of reading 4 GPIO pins using an interrupt.
(6.44 KiB) Downloaded 508 times
Good signatures never die. They just fade away.
Srikanth
User
Posts: 10
Joined: Thu 2016-08-18 9:03

Re: VS1005 MP3 Player with USB Host

Post by Srikanth »

Thank you Henrik and Panu,

I will work on it and get back to you.

Regards,
Srikanth
User avatar
Henrik
VLSI Staff
Posts: 1294
Joined: Tue 2010-06-22 14:10

Re: VS1005 MP3 Player with USB Host

Post by Henrik »

Hello again!

An alternative way to take control of the interrupts is provided in a new, general interrupt demo, here:
viewtopic.php?f=13&t=1972

That demo shows how to take control of any VS1005g interrupt.

Kind regards,
- Henrik
Good signatures never die. They just fade away.
Post Reply