------------------------------------------------------------------------------------------------------------------------------

交叉编译器:arm-linux-gcc-4.5.4

Linux内核版本:Linux-3.0

主机操作系统:Centos 6.5

开发板:FL2440

温度传感器:ds18b20

注:此程序的客户端是在装有ds18b20模块并有ds18b20驱动的系统上跑的,本人写的ds18b20的驱动

------------------------------------------------------------------------------------------------------------------------------

以下操作是建立在你有sqlite3数据库的情况下,sqlite3数据库的安装参考链接:http://www.linuxidc.com/Linux/2012-07/66854.htm

注:数据库安装好之后会在/home下自动创建一个sqlite-3.6.18的用户,其中保存了数据库sqlite3所有的执行文件,头文件还有库函数。

以下程序实现的功能是:客户端读取温度传感器的温度以及当时的时间,并向服务器发送数据。若连接服务器失败则保存数据到数据库。等待客户端可以连接上服务器的时候把保存的数据发送给服务器。

一、客户端代码

 /*********************************************************************************
* Copyright: (C) 2016 2013dianxin_3
* All rights reserved.
*
* Filename: mclient.c
* Description: This file
*
* Version: 1.0.0(08/16/2016)
* Author: xiaohexiansheng <1392195453@qq.com>
* ChangeLog: 1, Release initial version on "08/16/2016 07:16:44 PM"
*
********************************************************************************/
#include <sys/types.h>
#include <sys/ioctl.h>
#include <termios.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <sys/time.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <sqlite3.h> #define MAXLINE 4096
char get_sql[];
/********************************************************************************
* Description:
* Input Args:
* Output Args:
* Return Value:
********************************************************************************/
double get_tem(void) //获取温度的函数
{
int fd;
double result = ;
unsigned char buff[];
unsigned short temp = ;
int flag = ; if ((fd=open("/dev/ds18b20",O_RDWR | O_NDELAY | O_NOCTTY)) < )
{
perror("open device ds18b20 failed.\r\n");
exit();
} printf("open device ds18b20 success.\r\n"); read(fd, buff, sizeof(buff));
temp=((unsigned short)buff[])<<;
temp|=(unsigned short)buff[];
result=0.0625*((double)temp);
close(fd);
printf("temperature is %4f \r\n", result);
return result;
} int save_tem(char *s_temp) //将数据保存到数据库
{
char sql[];
sqlite3 *db;
FILE *fd; sqlite3_open("temperature.db", &db);
memset(sql, '\0', );
strcpy(sql, "create table tb(id INTEGER PRIMARY KEY, data TEXT)");
sqlite3_exec(db, sql, NULL, NULL, NULL); memset(sql, '\0', );
strcpy(sql, "insert into tb(data) values(\"");
strcat(sql, s_temp);
strcat(sql, "\")");
sqlite3_exec(db, sql, NULL, NULL, NULL);
sqlite3_close(db);
return ;
} int wf_callback(void *addr, int nr, char **values, char **names) //回掉函数依次将数据库中的数据发送给服务器
{ int sockfd;
char sendline[MAXLINE];
struct sockaddr_in servaddr; if((sockfd = socket(AF_INET, SOCK_STREAM, )) < )
{
printf("create socket error: %s(errno: %d).\n", strerror(errno), errno);
return ;
} memset(&servaddr, , sizeof(servaddr));
servaddr.sin_family = AF_INET;
servaddr.sin_port = htons();
if(inet_pton(AF_INET, addr, &servaddr.sin_addr) <= )
{
printf("inet_pton error for %s.\n", addr);
return ;
} memset(sendline, , sizeof(sendline));
if(connect(sockfd, (struct sockaddr*)&servaddr, sizeof(servaddr)) < )
{
printf("connect error: %s(errno: %d)\n", strerror(errno), errno);
return ;
} if(send(sockfd, values[], strlen(values[]), ) < )
{
printf("send msg error: %s(errno: %d)\n", strerror(errno), errno);
return ;
}
close(sockfd);
return ;
} int read_sql(char *addr) //读取数据库中的数据并发送的函数
{
char sql[];
sqlite3 *db; sqlite3_open("test.db", &db);
sqlite3_exec(db, "select * from tb", wf_callback, addr, NULL); //读取数据,并调用回调函数 sqlite3_close(db);
return ;
} int delet_sql(void) //删除数据库中表的函数
{
char sql[];
sqlite3 *db; sqlite3_open("test.db", &db);
sqlite3_exec(db, "DROP TABLE tb;", NULL, NULL, NULL); sqlite3_close(db);
return ;
} int main (int argc, char **argv)
{
double temperature;
int sockfd;
int ret;
char timE[];
time_t rawtime;
char temp[];
char sendline[MAXLINE];
char recvline[MAXLINE];
struct tm* timeinfo;
struct sockaddr_in servaddr; if(argc != ) //第二个参数为客户端的Ip地址,必须要有
{
printf("usage: ./client <ipaddress>.\n");
return ;
} if((sockfd = socket(AF_INET, SOCK_STREAM, )) < ) //打开一个socket的文件描述符
{
printf("create socket error: %s(errno: %d).\n", strerror(errno), errno);
return ;
} memset(&servaddr, , sizeof(servaddr));
servaddr.sin_family = AF_INET;
servaddr.sin_port = htons(); //使用6666号端口
if(inet_pton(AF_INET, argv[], &servaddr.sin_addr) <= )
{
printf("inet_pton error for %s.\n", argv[]);
return ;
} temperature = get_tem(); //获取温度值并返回给temperature
gcvt(temperature, , temp); //将温度值转换为字符串类型的
memset(sendline, , sizeof(sendline));
strcpy(sendline, "the degrees is ");
strcat(sendline, temp); memset(timE, , sizeof(timE));
time(&rawtime);
timeinfo=localtime(&rawtime);
strftime(timE,,"%y-%m-%d %I:%M:%S",timeinfo); //获取当前时间 strcat(sendline, "℃, time is ");
strcat(sendline, timE); if(connect(sockfd, (struct sockaddr*)&servaddr, sizeof(servaddr)) < )
{
ret = save_tem(sendline); //若连接客户端失败则调用save_tem函数保存数据
printf("connect error: %s(errno: %d)\n", strerror(errno), errno);
return ;
} if(send(sockfd, sendline, strlen(sendline), ) < )
{
printf("send msg error: %s(errno: %d)\n", strerror(errno), errno);
return ;
}
else
{
read_sql(argv[]); //如果可以连接数据库则读取数据库并发送
delet_sql(); //读取完了之后删除数据库
} close(sockfd); //关闭socket文件描述符
return ;
} /* ----- End of main() ----- */

二、服务器代码

 #include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<errno.h>
#include<sys/types.h>
#include<sys/socket.h>
#include<netinet/in.h>
#include <sys/time.h>
#include<time.h>
#include <sqlite3.h> #define MAXLINE 4096 int save_tem(char *s_temp)
{
char sql[];
sqlite3 *db;
FILE *fd; sqlite3_open("tem.db", &db);
memset(sql, '\0', );
strcpy(sql, "create table tb(id INTEGER PRIMARY KEY, data TEXT)");
sqlite3_exec(db, sql, NULL, NULL, NULL); memset(sql, '\0', );
strcpy(sql, "insert into tb(data) values(\"");
strcat(sql, s_temp);
strcat(sql, "\")");
sqlite3_exec(db, sql, NULL, NULL, NULL);
sqlite3_close(db);
return ;
} int main(int argc, char** argv)
{
int n;
int listenfd;
int connfd;
char buff[];
struct sockaddr_in servaddr; if((listenfd = socket(AF_INET, SOCK_STREAM, )) == - )
{
printf("create socket error: %s(errno: %d)\n",strerror(errno),errno);
exit();
} memset(&servaddr, , sizeof(servaddr));
servaddr.sin_family = AF_INET;
servaddr.sin_addr.s_addr = htonl(INADDR_ANY);
servaddr.sin_port = htons(); if(bind(listenfd, (struct sockaddr*)&servaddr, sizeof(servaddr)) == -)
{
printf("bind socket error: %s(errno: %d)\n",strerror(errno),errno);
exit();
} if(listen(listenfd, ) == -)
{
printf("listen socket error: %s(errno: %d)\n",strerror(errno),errno);
exit();
} printf("======waiting for client's request======\n"); while()
{
memset(buff, , sizeof(buff)); if((connfd = accept(listenfd, (struct sockaddr*)NULL, NULL)) == -)
{
printf("accept socket error: %s(errno: %d)",strerror(errno),errno);
continue;
}
n = recv(connfd, buff, MAXLINE, );
printf("%s\n", buff);
save_tem(buff);
close(connfd);
}
close(listenfd);
}

Linux下sqlite3编程的更多相关文章

  1. linux 下 poll 编程

    poll 与 select 很类似,都是对描述符进行遍历,查看是否有描述符就绪.如果有就返回就绪文件描述符的个数将.poll 函数如下: #include <poll.h> int pol ...

  2. Linux下Socket编程的端口问题( Bind error: Address already in use )

    Linux下Socket编程的端口问题( Bind error: Address already in use ) 在进行linux网络编程时,每次修改了源代码并再次编译运行时,常遇到下面的地使用错误 ...

  3. Linux 下IOport编程訪问

    曾经写的一篇笔记.偶尔翻出来了,放在这里做个纪念 Linux 下IOport编程訪问 这里记录的方法是在用户态訪问IOport,不涉及驱动程序的编写. 首先要包括头文件 /usr/include/as ...

  4. linux下socket编程实例

    linux下socket编程实例一.基本socket函数Linux系统是通过提供套接字(socket)来进行网络编程的.网络的socket数据传输是一种特殊的I/O,socket也是一种文件描述符.s ...

  5. Linux 下shell 编程学习脚手架

    linux body { font-family: Helvetica, arial, sans-serif; font-size: 14px; line-height: 1.6; padding-t ...

  6. linux下libnet编程 亲自测试可用

    linux下libnet编程 亲自测试可用 亲自测试  如果build包的时候 只要把类型改了 就能改成相应的协议. 0x0800 ip 0x0806 arp 0x86DD    IPv6 0x86e ...

  7. Linux下socket编程基本知识

    本文档主要讲解了Linux下socket编程的一些基本知识,主要包括套接字和字节序的概念,以及一些常用的结构体和函数. 本文是在网易云课堂学习过程中的记录,这个老师讲得很不错,推荐大家围观. Linu ...

  8. linux下socket编程

    相关结构 //下边这两个结构定义在<sys/types.h>里 //一般的地址结构,只能用于覆盖(把其他地址转换为此类型),且只能引用该地址的sa_family字段 struct sock ...

  9. Linux下串口编程【转】

    本文转载自:http://blog.csdn.net/w282529350/article/details/7378388 /************声明:本人只是见到这篇文章对我帮助很大才转载的,但 ...

随机推荐

  1. linux下检测可用串口并使用minicom打开

    目前使用minicom作为串口软件.但使用过程中,有一点感觉不方便的地方,就是我需要使用多个串口,当使用的不是串口0时,就要手动修改minicom的配置. 于是考虑实现脚本,自动列出当前串口,选择后调 ...

  2. 带你入门代理模式/SpringAop的运行机制

    SpringAop 是spring框架中最重要的一项功能之一,同时也是企业级开发记录事物日志等不可或缺的一部分,如果说你的系统需要记录用户访问接口的操作,那SpringAop是很完美的了,当然,拦截器 ...

  3. 【python】正则表达式相关

    注意:Python3.X 的print要有括号, Python 2.x的不需要 放上学习时写的例子: import re m = re.match(r'(\w+) (\w+)(?P<sign&g ...

  4. Opencv第三章

    2. 下面这个练习是帮助掌握矩阵类型.创造一个三通道二维矩阵,字节类型,大小为100×100,并设置所有数值为0. a. 在矩阵中使用void cvCircle(CvArr* img, CvPoint ...

  5. 使用Bind服务配置DNS服务器

    bind是什么 bind是DNS服务器软件 ,他的服务名称是named 功能区分: 正向解析:根据主机名查找对应的IP地址 反向解析:根据IP地址查找对应的主机名(域名) 工作形式上区分: 主服务器: ...

  6. 常用的LUA片段

    生成TS的办法 local t=ngx.now(); local n=os.date(,); n=n..-string.len(n)); ngx.say(n); 产生101至200的所有素数 func ...

  7. javaScript Promise 入门

    Promise是JavaScript的异步编程模式,为繁重的异步回调带来了福音. 一直以来,JavaScript处理异步都是以callback的方式,假设需要进行一个异步队列,执行起来如下: anim ...

  8. (十二)MySQL逻辑备份mysqldump

    (1)简介 语法 mysqldump -h服务器 -u用户名 -p密码 [-P端口号] [参数] 数据库名 >备份文件.sql 关于数据库: -A,--all-databases 所有库,会生成 ...

  9. 统计mysql库中每张表的行数据

    修改数据库配置文件:vim /etc/my.cnf [client] user=username password=password 使用shell脚本统计表中的行数据:count.sh #!/bin ...

  10. Dart基础

    dartpad在线调试  :https://dartpad.dartlang.org  运行需要用墙 vscode执行dart 安装 安装dart插件 下载安装dart 配置环境变量 vscode新建 ...