Skip to content

Instantly share code, notes, and snippets.

@willeccles
Last active November 10, 2023 21:09
Show Gist options
  • Save willeccles/e8bac6cee4dbee8c4939cdc2eec835c1 to your computer and use it in GitHub Desktop.
Save willeccles/e8bac6cee4dbee8c4939cdc2eec835c1 to your computer and use it in GitHub Desktop.
/* Compile with -DUSE_READLINE and -lreadline to use readline for input. */
#include <arpa/inet.h>
#include <errno.h>
#include <poll.h>
#include <signal.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <sys/socket.h>
#include <unistd.h>
#ifdef USE_READLINE
#include <readline/history.h>
#include <readline/readline.h>
#endif /* USE_READLINE */
#define NETBFRLEN 1024
int clientsocket;
void closeclient() {
if (clientsocket != -1 && clientsocket != 0) {
// shutdown(clientsocket, SHUT_WR);
// shutdown(clientsocket, SHUT_RD);
close(clientsocket);
}
}
void sighandler(int s) {
closeclient();
_exit(0);
}
int main(int argc, char** argv) {
if (argc == 1) {
fprintf(stderr, "Please supply address and port\n");
return 1;
}
struct sigaction sigint_handler;
sigint_handler.sa_handler = sighandler;
sigemptyset(&sigint_handler.sa_mask);
sigint_handler.sa_flags = 0;
sigaction(SIGINT, &sigint_handler, NULL);
char inbuffer[NETBFRLEN] = {0};
struct sockaddr_in server_addr;
socklen_t addr_size;
if ((clientsocket = socket(PF_INET, SOCK_DGRAM, 0)) == -1) {
perror("socket");
return 1;
}
server_addr.sin_family = AF_INET;
server_addr.sin_port = htons(atoi(argv[2]));
server_addr.sin_addr.s_addr = inet_addr(argv[1]);
memset(server_addr.sin_zero, 0, sizeof(server_addr.sin_zero));
addr_size = sizeof(server_addr);
#if 0
if (connect(clientsocket, (struct sockaddr*)&serverAddr, addr_size) == -1) {
perror("connect");
return 1;
}
#endif
#ifndef USE_READLINE
char input[256] = {0};
#else
char* input;
#endif /* USE_READLINE */
ssize_t outbytes, inbytes;
int status;
struct pollfd pfd;
pfd.events = POLLIN;
pfd.fd = clientsocket;
puts("Enter SCPI commands here.\n"
"Queries will timeout after 1 second.\n"
"Type 'quit', 'exit', or Control-C to quit.");
#ifdef USE_READLINE
puts("Readline line editing features are supported.");
#endif /* USE_READLINE */
while (1) {
#ifndef USE_READLINE
printf("> ");
scanf(" %253[^\n]", input);
#else
input = readline("> ");
if (!input) {
closeclient();
return 0;
}
#endif /* USE_READLINE */
if (0 == strcmp(input, "quit") || 0 == strcmp(input, "exit")) {
closeclient();
return 0;
}
#ifdef USE_READLINE
add_history(input);
#endif /* USE_READLINE */
size_t l = strlen(input);
#ifdef USE_READLINE
input = realloc(input, l + 3);
if (!input) {
perror("realloc");
closeclient();
return 1;
}
#endif /* USE_READLINE */
strcpy(input + l, "\r\n");
// outbytes = write(clientsocket, input, strlen(input));
outbytes = sendto(clientsocket, input, strlen(input), 0,
(struct sockaddr*)&server_addr, addr_size);
if (outbytes == -1) {
perror("write");
closeclient();
return 1;
}
if (NULL != strchr(input, '?')) {
status = poll(&pfd, 1, 1000);
if (status == 0) {
printf("No response from server within 1 second!\n");
} else if (status == -1) {
perror("poll");
closeclient();
return 1;
} else {
inbytes = read(clientsocket, inbuffer, NETBFRLEN);
if (inbytes == -1) {
perror("read");
closeclient();
return 1;
}
printf("%s", inbuffer);
memset(inbuffer, 0, NETBFRLEN);
}
}
#ifdef USE_READLINE
free(input);
#endif /* USE_READLINE */
}
return 0;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment