

#include "utility.h"
float myatof(const char* str)
{
	
	uint32_t int_nu = 0;
	uint32_t flot_nu = 0;
	float val;
	float f_count = 1;
	while((*str != 0) && (*str != '.'))
	{
		if(*str > '9' && *str < '0')
		{
			str++;
			continue;
		}
		int_nu = int_nu*10+(*str - 48);
		str++;
	}
	
	if(*str == 0)
	{
		val = int_nu;
		return val;
	}
	str++;
	while(*str != 0)
	{
		if(*str > '9' && *str < '0')
		{
			str++;
			continue;
		}
		flot_nu = flot_nu*10+(*str - 48);
		f_count *= 10;
		str++;
	}
	val = flot_nu;
	val = val / f_count + int_nu;
	return val;
}

/**
*@brief	 	string to uint16_t
*@param		str:src string， base:
*@return	num:convert result
*/
uint16_t atoi16(const char* str,uint16_t base)
{
  unsigned int num = 0;
  while (*str !=0)
          num = num * base + c2d(*str++);
  return num;
}

/**
*@brief	 	string to uint32
*@param		str:src string， base:
*@return	num:convert result
*/
uint32_t atoi32(const char* str,uint16_t base)
{
  uint32_t num = 0;
  while (*str !=0)
          num = num * base + c2d(*str++);
  return num;
}

/**
*@brief	 	uint16 data to string
*@param		n:src num， str[5]:string buffer  len：string size
*@return	void
*/
void myitoa(int n,char *str, int len)
{
  
  uint8_t i=len-1;

  memset(str,0x20,len);
  do{
  str[i--]=n%10+'0';
  
 }while((n/=10)>0);

 return;
}


/**
*@brief	 	dec or hex string convert to uint32_t
*@param		str:src string， ret： the pointer of result
*@return	success = 1, fail = 0
*/
int validatoi(const char* str, int base,uint32_t* ret)
{
  int c;
  const  char* tstr = str;
  if(str == 0 || *str == '\0') 
  {
  	return 0;
	}
  while(*tstr != '\0')
  {
    c = c2d(*tstr);
    if( (c >= 0) && (c < base))
	{
		 tstr++;
	}
    else
	{
	    return 0;
	}
  }
  
  *ret = atoi32(str,base);
  return 1;
}

/**
*@brief	 	 new char to replace the old char 
*@param		str:src string，oldchar:dst char，newchar：src char
*@return	void
*/
void replacetochar(char * str,	char oldchar,char newchar)
{
  int x;
  for (x = 0; str[x]; x++) 
    if (str[x] == oldchar) str[x] = newchar;	
}

/**
*@brief	 	char to num
*@param		c:src char
*@return	convert result
*/
char c2d(const uint8_t c)
{
	if (c >= '0' && c <= '9')
		return c - '0';
	if (c >= 'a' && c <= 'f')
		return 10 + c -'a';
	if (c >= 'A' && c <= 'F')
		return 10 + c -'A';

	return (char)0;
}
/**
*@brief	 	num to char
*@param		c:src num
*@return	convert result
*/
char d2c(const uint8_t c)
{
	if ( c <= 9)
	{
		return c + '0';
	}
	if (c >= 0x0a && c <= 0x0f)
	{
		return c + 'a' - 10;
	}
    return 0;
}

/**
*@brief	 	2bytes swap 
*@param		i:src num
*@return	convert result
*/
uint16_t swaps(uint16_t i)
{
  uint16_t ret=0;
  ret = (i & 0xFF) << 8;
  ret |= ((i >> 8)& 0xFF);
  return ret;	
}
/**
*@brief	 	4 bytes swap, bytes order 4 3 2 1 convert to 1 2 3 4
*@param		i:src num
*@return	convert result
*/
uint32_t swapl(uint32_t l)
{
  uint32_t ret=0;
  ret = (l & 0xFF) << 24;
  ret |= ((l >> 8) & 0xFF) << 16;
  ret |= ((l >> 16) & 0xFF) << 8;
  ret |= ((l >> 24) & 0xFF);
  return ret;
}

/**
*@brief	 	get substring
*@param		src:src string s1: target begin s2: target end sub: result pointer
*@return	void
*/
void mid(const char* src, const char* s1, const char* s2, char* sub)
{
	char* sub1;
	char* sub2;
	uint16_t n;

  sub1=strstr(src,s1);
  sub1+=strlen(s1);
  sub2=strstr(sub1,s2);
  n=sub2-sub1;
  strncpy(sub,sub1,n);
  sub[n]=0;
}
/**
*@brief	 	bytes array conver to string 
*@param		*data: ponit src bytes len: array length str: resuter string pointer
*@return	void
*/
	
void bytes2hexString(const char* data, uint32_t len, char* str)
{
	char c_temp;
	while(len > 0)
	{
		c_temp = ((*data) &0xF0) >> 4;
		if(c_temp < 10)
		{
			*str = c_temp + '0';
		}
		else
		{
			*str = (c_temp - 10) + 'A';
		}
		
		c_temp = ((*data) &0x0F);
		str++;
		if(c_temp < 10)
		{
			*str = c_temp + '0';
		}
		else
		{
			*str = (c_temp - 10)+ 'A';
		}
		str++;
		data++;
		len--;
	}
	*(str++) = '\0';
	
}
/*
Hex Datas to Bytes
*/
uint8_t HexStrings2Byte(char**strs,uint16_t size,uint8_t* buf,uint16_t buf_size)
{
	char* str;
	uint8_t data = 0;
	uint16_t count = 0;
	while((size > 0) && (count < buf_size))
	{
		str = strs[count++];
		size--;
		data = 0;
		while(*str != '\0')
		{
			
			if(*str == '0')
			{
				if((*(str+1) == 'X') || (*(str+1) == 'x'))
				{
					str+=2;
					continue;
				}
			}
			data <<=4;
			data |=c2d(*str);
			str++;
		}
		*buf = data;
		buf++;
	}
	return count;
}


/*
Hex Datas to uint32_t
*/
uint32_t HexStrings2UInt(char*str)
{

	uint32_t data = 0;
	uint16_t count = 0;
		data = 0;
		while(*str != '\0' && count < 10)
		{
			
			if(*str == '0')
			{
				if((*(str+1) == 'X') || (*(str+1) == 'x'))
				{
					str+=2;
					continue;
				}
			}
			data <<=4;
			data |=c2d(*str);
			str++;
			count++;
		}
	return data;
}

//冒泡排序16位数据
void Bubble_Sort_u16(uint16_t* buf,uint32_t len)
{
	uint32_t ul_temp1 = 0;
	uint32_t ul_temp2 = 0;
	uint16_t us_temp;
	if(len < 2)
		return;
	for(ul_temp2 = 0; ul_temp2 < len-1; ul_temp2++)
	{
		for(ul_temp1 = 0; ul_temp1 < len-1-ul_temp2; ul_temp1++)
		{
			if(buf[ul_temp1] > buf[ul_temp1+1])
			{
				us_temp = buf[ul_temp1];
				buf[ul_temp1] = buf[ul_temp1 + 1];
				buf[ul_temp1 + 1] = us_temp;
			}
		}
	}
	
}
//数据左移
void BufMoveLeft(uint8_t* srcbuf,uint16_t offset,uint16_t data_len)
{
	uint8_t index = 0;
	while(data_len > 0)
	{
		srcbuf[index] = srcbuf[index+offset];
		data_len--;
		index++;
	}
}
//数据右移
void BufMoveRight(uint8_t* srcbuf,uint16_t offset,uint16_t data_len)
{
	while(data_len > 0)
	{
		data_len--;
		srcbuf[data_len+offset] = srcbuf[data_len] ; 
	}
}


//@brief 计算数组的CRC8值
//@param *srcbuf 数据源指针
//@param len 数据源长度
//@rtvl 返回计算结果
uint8_t CheckXOR_8(uint8_t* srcbuf,uint16_t len)
{
  uint8_t crc = 0x00;
  while(len--)
  {
    crc ^= *srcbuf++;
  }
  return crc;
}


//@brief 计算数组异或校验值
//@param *Ptr 数据源
//@param num 计算长度
//@rtvl 返回计算结果
uint8_t CheckCRC_8(uint8_t* Ptr,uint16_t num)
{
  uint8_t crc = 0;
	uint16_t j,i;
	
    for (j = 0; j < num; j++)
    {
        crc ^= *(Ptr+j);
        for ( i = 0; i < 8; i++)
        {
            if ((crc & 0x01) != 0)
            {
                crc >>= 1;
                crc ^= 0x8c;
            }
            else
            {
                crc >>= 1;
            }
        }
    }
    return crc;
}
 //@brief 计算CRC32
//@param *srcbuf 数据源
//@param len 计算长度
//@rtvl 返回计算结果
uint32_t Crc32Calu(uint32_t* buf, uint32_t len)
{
	 uint32_t temp,crc = 0xFFFFFFFF;

	 uint32_t i,j;
	 i = 0;
	 if(((uint32_t)buf %4) != 0)
	 {
			 return 1;
	 }
	 while(i<len)
	 {
			temp = *buf;
			i += 4;
			buf ++;
			for(j=0; j<32; j++)
			{
					if( (crc ^ temp) & 0x80000000 )
					{
							crc = 0x04C11DB7 ^(crc<<1);
					}
					else
					{
							crc <<=1;
					}
					temp<<=1;
			}
			crc&=0xFFFFFFFF;
	 }
	 return crc;
}
/*
@brief 获取数组中的最大值和最小值
@param *aus_buf 缓存数组
@param us_size 数组长度
@param *us_max 最大值
@param *us_min 最小值
*/

void GetMaxAndMinValue(uint16_t* aus_buf,uint16_t us_size,uint16_t* us_max,uint16_t* us_min)
{
	*us_max = 0;
	*us_min = ~0;
	while(us_size > 0)
	{
		if(*us_max < *aus_buf)
		{
			*us_max = *aus_buf;
		}
		if(*us_min > *aus_buf)
		{
			*us_min = *aus_buf;
		}
		aus_buf++;
		us_size--;
	}
}
