Best way to send sprintf HTML data

AgentSmithers
Posts: 195
Joined: Sat Apr 01, 2017 1:21 am
Contact:

Best way to send sprintf HTML data

Postby AgentSmithers » Thu Mar 01, 2018 8:08 am

Hi Everyone!
I host a TCP 80 Webserver on my ESP, I use makefile to burn my html file with a few %s variable inside the HTML. I then use spiflash read API to read the HTMl into a ZALLOC then use sprintf to massage the HTML then I send it out. While that's great and all the HTML can be a bit heavy near the 6k range of byte data. Anyone have any suggestions on how to massage the data perhaps in the SPIflash memory verses uses the heap or any other suggestions?

AgentSmithers
Posts: 195
Joined: Sat Apr 01, 2017 1:21 am
Contact:

Re: Best way to send sprintf HTML data

Postby AgentSmithers » Thu Mar 01, 2018 3:27 pm

Okay, I need a C99 Guru here.. SpiRead has to be 4 bytes Aligned so anyone a how to do this or maybe a more effective approch. I was trying to check how many % signs there were in the 4 byte string, Call SprintF to edit the string then loop through the SPI flash to have it format the string in one call instead of using SPIRead to load the string into a Malloc then having to Malloc once again to use sprintf. This will save me ALOT of heap space if I can just sprintf it stright from flash.
Any assistance will be much appreciated.


Code: Select all

#include <stdarg.h> //Required for VAList
void flashsprintf(char *s, uint32_t address, int n, ...)
{

   int ret;
   int val;
   va_list ap;
   va_start(ap, n);

   int numberOfVars = 0;
   int i, ii = 0;
   char * ss = s; //Backup Ptr
   for (numberOfVars=0; s[i]; s[i]=='%' ? numberOfVars++ : *s++);
   s = ss; //RestorePtr

   os_printf("start\r\n");
   for (i=0; i<=(os_strlen(s)-1); i++)
   {
      //os_printf("%d-%c\r\n", i, s[i]);
      if (s[i] == '%')
      {
         switch(s[i+1])
         {
            case 's'  :
            val=va_arg(ap,char *);
            break; /* optional */

            case 'd'  :
            os_printf("Dec ");
            val=va_arg(ap,int);
            break; /* optional */

            /* you can have any number of case statements */
            default : /* Optional */
            os_printf("Unknown ");
         }
      }
   }

   os_printf("%d", i);

   
   
   for (ii=0;ii<i;ii++)
   {
      val=va_arg(ap,int);
      os_printf (" %d",val);
   }      
   //ret = vsprintf(s, fmt, ap);
   va_end(ap);
   return ret;
}

AgentSmithers
Posts: 195
Joined: Sat Apr 01, 2017 1:21 am
Contact:

Re: Best way to send sprintf HTML data

Postby AgentSmithers » Fri Mar 02, 2018 3:23 am

Code: Select all

#include "stdafx.h"
#include <stdio.h>
#include <string.h>
#include <stdlib.h>
#include <stdarg.h> //Required for VAList

#define _CRT_SECURE_NO_WARNINGS

int flashsprintf(char *buffer, char *s, int n, ...)
{

   int ret;
   void * val;

   void * args[4];

   va_list ap;
   va_start(ap, n);

   int numberOfVars = 0;
   int i, ii, index = 0;
   char * ss = s; //Backup Ptr
   for (numberOfVars = 0; s[numberOfVars]; s[numberOfVars] == '%' ? numberOfVars++ : *s++);
   s = ss; //RestorePtr

   printf("start\r\n");
   for (i = 0; i <= (strlen(s) - 1); i++)
   {
      //os_printf("%d-%c\r\n", i, s[i]);
      if (s[i] == '%')
      {
         switch (s[i + 1])
         {
         case 's':
            args[index] = va_arg(ap, char *);
            index++;
            break; /* optional */

         case 'd':
            //int *p1 = (int *)malloc(sizeof(int));
            //p1 = &va_arg(ap, int);
            //args[index] = p1;
            args[index] = (void *)va_arg(ap, int);
            index++;
            break; /* optional */
                  /* you can have any number of case statements */
         //default: /* Optional */
            //printf("Unknown ");
         }
      }
   }

   switch (index - 1)
   {
      case 0:
         sprintf(buffer, s, args[0]);
      case 1:
         sprintf(buffer, s, args[0], args[1]);
      case 2:
         sprintf(buffer, s, args[0], args[1], args[2]);
      default:
         printf("default");
   }
   

   printf("%d", i);


   /*
   for (ii = 0; ii<i; ii++)
   {
      val = va_arg(ap, int);
      printf(" %d", val);
   }
   */
   //ret = vsprintf(s, fmt, ap);
   va_end(ap);
   return 0;
}

int main()
{
   char buffer[512];
   flashsprintf(buffer, "%s%d%s", 3, "test", 5, "tester");
    return 0;
}



Okay I developed this on windows but porting the idea wont be so bad. Any idea on how to optimize the switch statement so I don't have to expand the variables the way I did in sprintf once I integrate SPI and as I loop through the SPI data?

AgentSmithers
Posts: 195
Joined: Sat Apr 01, 2017 1:21 am
Contact:

Re: Best way to send sprintf HTML data

Postby AgentSmithers » Tue Mar 06, 2018 1:06 am

Hey everyone just checking back. So this is the outcome of my work and discovery.
I hope this helps. This will adjust the SprintF on the fly out of flash memory. It's hardly tested but the idea is there and it worked with that I threw at it.

Code: Select all

char buffer[5000];
flashsprintf(buffer, HTMLIndexMemorySpace, 3, “MyString1”, “MyString2”, “MyString3”);
os_printf(buffer);

 
void flashsprintf(char * dest, uint32_t address, int n, …)
{
int i = 0;
int ii = 0;
int ret;
int val;

va_list ap;
va_start(ap, n);

int numberOfVars = 0;

uint16 destindex = 0;
uint16 addressindex = 0;
char buffer[4];
bool percentflag = false; //This Flag is used for if the last char is a %
while(true)
{
system_soft_wdt_feed();
if (spi_flash_read(address+(addressindex*4), buffer, 4) != 0)
{
os_printf(“Read failed at offset=0x%02x index=%d\r\n”, address, index);
return 0;
}
os_printf(“string: %d – %c%c%c%c\r\n”, (addressindex*4), *(buffer), *(buffer+1), *(buffer+2), *(buffer+3));
addressindex++;
for (i=0; i<=3; i++)
{
if (percentflag)
{
switch(buffer[i])
{
case ‘s’ :
val=va_arg(ap,char *);
destindex += os_sprintf(dest+destindex, “%s”, val);
break; /* optional */

case ‘d’ :
val=va_arg(ap,int);
destindex += os_sprintf(dest+destindex, “%d”, val);
break; /* optional */

/* you can have any number of case statements */
default : /* Optional */
os_printf(“Unknown “);

}
os_printf(“Removing %%”);
percentflag = false;
}

if (buffer[i] == ‘%’)
{
os_printf(“Setting %%”);
percentflag = true;
continue;
}
else
{
*(dest+destindex)=buffer[i];
destindex++;
if (os_strncmp((dest+destindex-7), “</html>”, 7) == 0)
{
*(dest+destindex)=0x00;
os_printf(“Exiting”);
return;
}
}
}
}

os_printf(“done”);
va_end(ap);
return ret;
}

Who is online

Users browsing this forum: No registered users and 164 guests