๐Ÿ˜Ž ๊ณต๋ถ€ํ•˜๋Š” ์ง•์ง•์•ŒํŒŒ์นด๋Š” ์ฒ˜์Œ์ด์ง€?

[์ž๋™์ฐจ ๋’ทํŽธ์— LCDํŒ์œผ๋กœ ์ƒํ™ฉ ์ „๋‹ฌํ•˜๊ธฐ 5] client ์—์„œ ๋ฐ›์€ message ๋ฅผ serial ํ†ต์‹  ํ†ตํ•ด arduino ๋กœ ์ „์†ก by.termios ๋ณธ๋ฌธ

๐Ÿ‘ฉ‍๐Ÿ’ป IoT (Embedded)/Arduino

[์ž๋™์ฐจ ๋’ทํŽธ์— LCDํŒ์œผ๋กœ ์ƒํ™ฉ ์ „๋‹ฌํ•˜๊ธฐ 5] client ์—์„œ ๋ฐ›์€ message ๋ฅผ serial ํ†ต์‹  ํ†ตํ•ด arduino ๋กœ ์ „์†ก by.termios

์ง•์ง•์•ŒํŒŒ์นด 2023. 11. 10. 12:12
728x90
๋ฐ˜์‘ํ˜•

โญ client ์—์„œ ๋ฐ›์€ message ๋ฅผ serial ํ†ต์‹  ํ†ตํ•ด arduino ๋กœ ์ „์†ก

 

โญ server.c

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <arpa/inet.h>
#include <sys/socket.h>

#define BUF_SIZE 16
void error_handling(char *message);

int main(int argc, char *argv[])
{
   // ์„œ๋ฒ„, ํด๋ผ์ด์–ธํŠธ ์†Œ์ผ“ ํŒŒ์ผ๋””์Šคํฌ๋ฆฝํ„ฐ ๋ณ€์ˆ˜ ์„ ์–ธ
   int serv_sock, clnt_sock;
   char message[BUF_SIZE];
   int str_len, i;

   // sockaddr_in ๊ตฌ์กฐ์ฒด ๋ณ€์ˆ˜ ์„ ์–ธ
   struct sockaddr_in serv_adr, clnt_adr;
   socklen_t clnt_adr_sz;

   if(argc != 2)
   {
      printf("Usage : %s <port>\n", argv[0]);
      exit(1);
   }

   // ----------- 1. Create socket object ------------------
   // socket() : socket ์ƒ์„ฑ & socket discriptor
   serv_sock = socket(PF_INET, SOCK_STREAM, 0);
   if(serv_sock == -1)
      error_handling("socket() error");


   // ----------- 2. Bind the socket file ------------------
   // serv_sock์— bind ๋กœ ์ฃผ์†Œ ๋„ฃ๊ธฐ ์œ„ํ•œ ๋ฐ‘์ž‘์—…
   memset(&serv_adr, 0, sizeof(serv_adr));

   // Prepare the address
   serv_adr.sin_family = AF_INET;                     // type : IPv4
   serv_adr.sin_addr.s_addr = htonl(INADDR_ANY);      // ip์ฃผ์†Œ
   serv_adr.sin_port = htons(atoi(argv[1]));          // ํฌํŠธ๋ฒˆํ˜ธ

   // bind()๋กœ ์„œ๋ฒ„ ์†Œ์ผ“์— ์ฃผ์†Œ์ •๋ณด ํ• ๋‹น
   if(bind(serv_sock, (struct sockaddr*)&serv_adr, sizeof(serv_adr)) == -1)
      error_handling("bind() error");

   // ----------- 3. Prepare backlog ------------------
   // listen()์œผ๋กœ ์„œ๋ฒ„์†Œ์ผ“์œผ๋กœ ์˜ค๋Š” ํด๋ผ์ด์–ธํŠธ ์š”์ฒญ ๋Œ€๊ธฐ
   if(listen(serv_sock, 5) == -1)
      error_handling("listen() error");

   clnt_adr_sz = sizeof(clnt_adr);

   for(i = 0; i < 5; i++)
   {
      printf("Listen....\n");
      
      // ----------- 4. Start accepting clients ---------
      // ํด๋ผ์ด์–ธํŠธ ์ ‘์† ์š”์ฒญ ๋Œ€๊ธฐ ๋ฐ ์ˆ˜๋ฝ, ํด๋ผ์ด์–ธํŠธ์™€์˜ ํ†ต์‹ ์„ ์œ„ํ•œ ์ƒˆ socket ์ƒ์„ฑ
      clnt_sock = accept(serv_sock, (struct sockaddr*)&clnt_adr, &clnt_adr_sz);
      if(clnt_sock == -1)
         error_handling("accept() error");
      else
         printf("Connected client %d \n", i + 1);

      // ํด๋ผ์ด์–ธํŠธ๋กœ๋ถ€ํ„ฐ ์ „์†ก๋œ ์ž๋ฃŒ ์ˆ˜์‹ 
      // read(int fd, void *buff, size_t nbytes)
      while((str_len = read(clnt_sock, message, BUF_SIZE)) != 0)
         // ํด๋ผ์ด์–ธํŠธ๋กœ ์ž๋ฃŒ ์†ก์‹ 
         // write(int fd, const void *buf, size_t nbytes);
         write(clnt_sock, message, str_len);
      
      // ํ†ต์‹ ์„ ์™„๋ฃŒํ•˜๋ฉด socket ์„ ์†Œ๋ฉธ
      close(clnt_sock);
   }

   // ํ†ต์‹ ์„ ์™„๋ฃŒํ•˜๋ฉด socket ์„ ์†Œ๋ฉธ
   close(serv_sock);
   return 0;
}

void error_handling(char *message)
{
   fputs(message, stderr);
   fputc('\n', stderr);
   exit(1);
}

 

โญ client.c

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <arpa/inet.h>
#include <sys/socket.h>

#include <fcntl.h>
#include <termios.h>

#define BUF_SIZE 16
void error_handling(char *message);

typedef struct
{
   // ํŒŒ์ผ ๋””์Šคํฌ๋ฆฝํ„ฐ : ์–ด๋– ํ•œ ํ†ต์‹  ํฌํŠธ๋ฅผ ์—ด์—ˆ์„ ๋•Œ ์ปดํ“จํ„ฐ๊ฐ€ ์ฐพ์•„๊ฐ€๊ธฐ ์‰ฝ๊ฒŒ ์ •์ˆ˜๋กœ ์ˆซ์ž ๋งค๊น€
   int fd;
} SerialPort;

// device : ์—ด๊ณ  ์‹ถ์€ ์‹œ๋ฆฌ์–ผ ํฌํŠธ์˜ ์ด๋ฆ„
int serial_open(SerialPort *port, const char *device)
{
   // open : ๋ฌธ์ž์—ด๋กœ ์„ ์–ธ๋œ ๊ฒฝ๋กœ(device)๋ฅผ ๋ฐ›์•„์„œ ํŒŒ์ผ ๋””์Šคํฌ๋ฆฝํ„ฐ(fd)๋กœ ๋ฐ˜ํ™˜ํ•˜๋Š” ํ•จ์ˆ˜
   port->fd = open(device, O_RDWR | O_NOCTTY | O_NDELAY);
   if (port->fd == -1)
   {
      perror("Unable to open port");
      return -1;
   }

   // ์‹œ๋ฆฌ์–ผ ํ†ต์‹  ํ™˜๊ฒฝ์„ ์„ค์ •ํ•˜๊ธฐ ์œ„ํ•ด termios ๊ตฌ์กฐ์ฒด๋ฅผ ์„ ์–ธ
   struct termios options;

   memset(&options, 0, sizeof(options));

   // ์‹œ๋ฆฌ์–ผ ํฌํŠธ ์ดˆ๊ธฐํ™”
   tcflush(port->fd, TCIFLUSH); 

   // Terminer Control ๋ชจ๋“œ ์„ค์ •์„ ์œ„ํ•ด์„œ Get
   tcgetattr(port->fd, &options); 
   cfsetispeed(&options, B9600); // Set baud rate to 9600 (adjust as needed)
   cfsetospeed(&options, B9600);

   options.c_cflag |= CS8;     // 8 data bits -> ๋ฌธ์ž ํฌ๊ธฐ ๋งˆ์Šคํฌ
   options.c_cflag &= ~PARENB; // No parity -> PARENB : ์ถœ๋ ฅ ์‹œ ํŒจ๋ฆฌํ‹ฐ ์ƒ์„ฑ์„ ํ™œ์„ฑํ™”ํ•˜๊ณ  ์ž…๋ ฅ
   options.c_cflag &= ~CSTOPB; // One stop bit -> CSTOPB : Stop bit ์ˆ˜ 1๊ฐœ
   // options.c_cflag &= ~CSIZE;  // Mask the character size bits
   
   // Serial Port์— ์ƒˆ ์„ค์ • Set
   // ์‹œ๋ฆฌ์–ผ ํฌํŠธ์— ์„ค์ • ์ž…๋ ฅ (TCSANOW : ์ฆ‰์‹œ ์†์„ฑ์„ ๋ณ€๊ฒฝ์‹œ์ผœ๋ผ)
   tcsetattr(port->fd, TCSANOW, &options);

   return 0;
}

void serial_close(SerialPort *port)
{
   close(port->fd);
   port->fd = -1;
}

int serial_read(SerialPort *port, char *buffer, size_t size)
{
   // Serial Port๋กœ๋ถ€ํ„ฐ ๋ฐ์ดํ„ฐ ์ˆ˜์‹ 
   // read์— ์˜ํ•ด์„œ ์‹ค์ œ๋กœ ์ฝํ˜€์ง„ ๋ฌธ์ž์˜ ๊ฐœ์ˆ˜๋ฅผ ๊ฐ–๊ฒŒ ๋จ
   return read(port->fd, buffer, size);
}

ssize_t serial_write(SerialPort *port, char *buffer, size_t size)
{
   // Serial Port์œผ๋กœ ๋ฐ์ดํ„ฐ ์†ก์‹ 
   return write(port->fd, buffer, size);
}

int main(int argc, char *argv[])
{
   int sock;
   char message[BUF_SIZE] = {0, };
   int str_len;

   // sockaddr_in ๊ตฌ์กฐ์ฒด ๋ณ€์ˆ˜ ์„ ์–ธ
   struct sockaddr_in serv_adr;

   if (argc != 3)
   {
      printf("Usage : %s <IP> <port> \n", argv[0]);
      exit(1);
   }

   // ----------- 1. Create socket object ------------------
   // socket() : socket ์ƒ์„ฑ & socket discriptor
   sock = socket(PF_INET, SOCK_STREAM, 0);
   if (sock == -1)
      error_handling("socket() error");

   // serial port
   SerialPort port;
   if (serial_open(&port, "/dev/ttyACM0") == -1)
   {
      return -1;
   }

   // ------------ 2. Connect to server-- ------------------
   // serv_sock์— bind ๋กœ ์ฃผ์†Œ ๋„ฃ๊ธฐ ์œ„ํ•œ ๋ฐ‘์ž‘์—…
   memset(&serv_adr, 0, sizeof(serv_adr));

   // Prepare the address
   serv_adr.sin_family = AF_INET;                     // type : IPv4
   serv_adr.sin_addr.s_addr = inet_addr(argv[1]);     // ip์ฃผ์†Œ
   serv_adr.sin_port = htons(atoi(argv[2]));          // ํฌํŠธ๋ฒˆํ˜ธ

   // ๋Œ€์ƒ ์„œ๋ฒ„ ์†Œ์ผ“์— ์ฃผ์†Œ ํ• ๋‹น
   // ์ฃผ์†Œ ์ •๋ณด์— ์„œ๋ฒ„์˜ ์ฃผ์†Œ์™€ ํฌํŠธ ๋ฒˆํ˜ธ๋ฅผ ์ง€์ •ํ•˜๊ณ  ์„œ๋ฒ„์™€ ์—ฐ๊ฒฐ ์‹œ๋„
   if (connect(sock, (struct sockaddr *)&serv_adr, sizeof(serv_adr)) == -1)
      error_handling("connect() error!");
   else
      puts("Connect........");

   while (1)
   {
      fputs("Input message(Q to quit) : ", stdout);
      fgets(message, BUF_SIZE, stdin);

      if (!strcmp(message, "q\n") || !strcmp(message, "Q\n"))
         break;
      
      // ํด๋ผ์ด์–ธํŠธ๋กœ ์ž๋ฃŒ๋ฅผ ์†ก์‹ ํ•œ๋‹ค
      // write(int fd, const void *buf, size_t nbytes);
      write(sock, message, strlen(message));

      // ํด๋ผ์ด์–ธํŠธ๋กœ๋ถ€ํ„ฐ ์ „์†ก๋œ ์ž๋ฃŒ ์ˆ˜์‹ ํ•œ๋‹ค
      // read(int fd, void *buff, size_t nbytes)
      str_len = read(sock, message, BUF_SIZE - 1);
      message[str_len] = 0;

      printf("Message form server : %s", message);

      // serial port ๋กœ message ์ „๋‹ฌ
      serial_write(&port, message, sizeof(message));      
   }
   
   // ํ†ต์‹  ํฌํŠธ๋ฅผ ๋‹ซ์•„ ์‚ฌ์šฉ์„ ์ค‘์ง€
   serial_close(&port);   

   close(sock);   
   return 0;
}

void error_handling(char *message)
{
   fputs(message, stderr);
   fputc('\n', stderr);
   exit(1);
}
728x90
๋ฐ˜์‘ํ˜•
Comments