編輯:關於Android編程
最近在做android native socket通信。主要在native這裡寫socket服務端的程序。根據client需求,通過PC端串口發送AT command,native負責接受從PC端發送的命令,過濾有效命令,通過socket發送到APP端,APP收到命令後進行相關測試,之後將測試信息返回native,native發送到PC端串口,顯示測試結果。
native的socket服務端的實現原理:創建後台服務,開啟一個進程,監聽串口消息。
流程如下:
1.在init.rc裡增加服務
chown system system /dev/ttyGS0
chmod 0666 /dev/ttyGS0
on property:ro.baseband="unknown"
start at
service at /system/bin/at
socket sockettest stream 0666 radio system
user system
group system inet
disabled
2.native服務程序 /system/at/at.c
#if 1
#define LOG_TAG "AT"
#define SOCKET_NAME "sockettest"
#include <utils/Log.h>
#include <stdio.h>
#include <stdlib.h>
#include <errno.h>
#include <string.h>
#include <sys/types.h>
#include <netinet/in.h>
#include <sys/socket.h>
#include <sys/wait.h>
#include <sys/un.h>
#include <cutils/sockets.h>
#include <fcntl.h> //open(), read(), write()
#define BUFSIZE 100
int count = 0;
#define LOGE(...) __android_log_print(ANDROID_LOG_ERROR, "myserver", __VA_ARGS__)
int main(){
#if 1
int connect_number = 4;
int fdListen = -1, new_fd = -1;
int fd, ret;
char ttyBuf[BUFSIZE];
char *msg = "";// "ttyGS0 test";
char *end = "\r\n";
struct sockaddr peeraddr;
socklen_t socklen = sizeof (peeraddr);
int numbytes ;
char buff[256];
fd_set fds;
int max = 0;
while(1){
fd = open("/dev/ttyGS0", O_RDWR);//打開usb serial device
//printf("envi serial test program\n");
LOGD("envi serial test program","myserver");
if(fd < 0)
{
//printf("\n");
LOGD("Error: open /dev/ttyGS0 error!","myserver");
return 1;
}
fdListen = android_get_control_socket(SOCKET_NAME);//創建native socket服務端本地連接
if (fdListen < 0) {
LOGD("Failed to get socket","myserver");
exit(-1);
}
LOGD("get","myserver");
ret = listen(fdListen, connect_number); //listen
if (ret < 0) {
LOGD("listen socket failed","myserver");
//perror("listen");
//exit(-1);
}
LOGD("geta","myserver");
//It block until client connected.accept(socket_id, &peeraddr, &socklen);
#if 1
new_fd = accept(fdListen, &peeraddr, &socklen); //與client端連接
if (new_fd < 0 ) {
//LOGD("Error on accept() errno:%d", errno);
LOGD("Error on accept()","myserver");
//perror("accept");
//exit(-1);
continue;
}
LOGD("getb","myserver");
//send at command from ttyGS0
while(1){
//read from ttyGS0
memset(ttyBuf, 0, sizeof(ttyBuf));
ret = read(fd, ttyBuf, BUFSIZE);
if(ret < 0)
{
//printf("Error: read device error!\n");
//return 1;
LOGD("Error: read device error","myserver",errno);
}
if(ttyBuf[0] != NULL){
LOGD("while count","myserver",ttyBuf[0]);
LOGD("myserver","yzy is " + ttyBuf[0]);
//strcat(ttyBuf, end);//add /r/n
if(send(new_fd, ttyBuf, strlen(ttyBuf), 0) < 0) {
LOGE("send failed");
}
LOGD("get1","myserver");
#if 1
FD_ZERO(&fds);
FD_SET(new_fd, &fds);
if(new_fd > max)
max = new_fd;
if(select(max + 1, &fds, NULL, NULL, NULL) < 0)//t進行讀操作
{
LOGE("select() failed","myserver");
}
if(FD_ISSET(new_fd, &fds)){
if((numbytes = recv(new_fd,buff,sizeof(buff),0))==-1)
{
LOGE("recv failed","myserver");
//perror("recv");
//exit(-1);
}
}
#endif
LOGD("get2","myserver");
if(numbytes > 0){
ret = write(fd, buff, strlen(buff));
if(ret < 0)
{
LOGD("write ttyGS0 error","myserver");
//return 1;
}
}
#endif
}
close(fd);
close(new_fd);
close(fdListen);
#endif
}
return 0;
}
#endif
3.APP端用localSocket來創建client端,用connect()函數來連接native socket server端。
LocalSocket ls = null;
LocalSocketAddress lsa;
ls = new LocalSocket();
lsa = new LocalSocketAddress(SOCKET_NAME,LocalSocketAddress.Namespace.RESERVED);//這裡的SOCKET_NAME必須與native和init.rc相同,為sockettest
ls.connect(lsa);
如果socket連上沒有問題,就可以收發消息了。
4.小結:native和framework的通信是通過jni,一般情況下是framework調用jni的。如果native有消息,怎麼樣讓framework知道呢?上面使用socket通信,可以讓framework和native相互通信。
Android中,要自己實現一個掛斷電話方法時,很久之前可以endCall().不過現在已經不行了,要應用反射機制,獲取到"android.os.Service
--------------------------------------廣播機制簡介-----------------------------------------
問題 在Android中使用內嵌的WebView加載HTML網頁時,如果html頁面中存在輸入框。那麼在有些手機設備中,當輸入框獲取焦點時,系統輸入法鍵盤無法正確彈出,從
1、itools模擬器模擬器內置文件管理器,可以方便地作開發時進行文件管理。 itools模擬器文件管理器 2、可輕松設置模擬器分辨率,支持平板分辨率設
最近自家的系統要做一個升級服務,裡面有三個功能,第一個是系統升級,也就是