Basic socket communication
This commit is contained in:
		
							
								
								
									
										104
									
								
								sources/ui-socket.c
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										104
									
								
								sources/ui-socket.c
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,104 @@
 | 
			
		||||
#include "ui-socket.h"
 | 
			
		||||
#include <errno.h>
 | 
			
		||||
#include <pthread.h>
 | 
			
		||||
#include <stdio.h>
 | 
			
		||||
#include <string.h>
 | 
			
		||||
#include <sys/socket.h>
 | 
			
		||||
#include <sys/un.h>
 | 
			
		||||
#include <unistd.h>
 | 
			
		||||
 | 
			
		||||
static int socket_fd = -1;
 | 
			
		||||
static pthread_mutex_t socket_mutex = PTHREAD_MUTEX_INITIALIZER;
 | 
			
		||||
 | 
			
		||||
int init_ui_socket(const char *filename) {
 | 
			
		||||
  struct sockaddr_un addr;
 | 
			
		||||
  int fd;
 | 
			
		||||
 | 
			
		||||
  if ((fd = socket(AF_UNIX, SOCK_STREAM, 0)) == -1) {
 | 
			
		||||
    perror("socket");
 | 
			
		||||
    return -1;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  memset(&addr, 0, sizeof(addr));
 | 
			
		||||
  addr.sun_family = AF_UNIX;
 | 
			
		||||
  strncpy(addr.sun_path, filename, sizeof(addr.sun_path) - 1);
 | 
			
		||||
 | 
			
		||||
  if (unlink(filename) == -1 && errno != ENOENT) {
 | 
			
		||||
    perror("unlink");
 | 
			
		||||
    close(fd);
 | 
			
		||||
    return -1;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  if (bind(fd, (struct sockaddr *)&addr, sizeof(addr)) == -1) {
 | 
			
		||||
    perror("bind");
 | 
			
		||||
    close(fd);
 | 
			
		||||
    return -1;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  if (listen(fd, 5) == -1) {
 | 
			
		||||
    perror("listen");
 | 
			
		||||
    close(fd);
 | 
			
		||||
    return -1;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  socket_fd = fd;
 | 
			
		||||
  return 0;
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
int ask_access(const char *filename, struct process_info pi) {
 | 
			
		||||
  int client_fd;
 | 
			
		||||
  struct sockaddr_un client_addr;
 | 
			
		||||
  socklen_t client_len = sizeof(client_addr);
 | 
			
		||||
  char request[1024];
 | 
			
		||||
  char response[4];
 | 
			
		||||
  ssize_t bytes_sent, bytes_received;
 | 
			
		||||
 | 
			
		||||
  // Accept a connection from the GUI
 | 
			
		||||
  if ((client_fd = accept(socket_fd, (struct sockaddr *)&client_addr,
 | 
			
		||||
                          &client_len)) == -1) {
 | 
			
		||||
    perror("accept");
 | 
			
		||||
    return -1;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  // Construct the request message
 | 
			
		||||
  snprintf(request, sizeof(request), "r%s;%d;%s;%d\0", filename, pi.PID,
 | 
			
		||||
           pi.name, pi.UID);
 | 
			
		||||
 | 
			
		||||
  // Lock the socket to ensure thread safety
 | 
			
		||||
  pthread_mutex_lock(&socket_mutex);
 | 
			
		||||
 | 
			
		||||
  // Send the request message to the GUI
 | 
			
		||||
  bytes_sent = send(client_fd, request, strlen(request), 0);
 | 
			
		||||
  if (bytes_sent == -1) {
 | 
			
		||||
    perror("send");
 | 
			
		||||
    pthread_mutex_unlock(&socket_mutex);
 | 
			
		||||
    close(client_fd);
 | 
			
		||||
    return -1;
 | 
			
		||||
  }
 | 
			
		||||
 | 
			
		||||
  // Receive the response from the GUI
 | 
			
		||||
  bytes_received = recv(client_fd, response, sizeof(response) - 1, 0);
 | 
			
		||||
  if (bytes_received == -1) {
 | 
			
		||||
    perror("recv");
 | 
			
		||||
    pthread_mutex_unlock(&socket_mutex);
 | 
			
		||||
    close(client_fd);
 | 
			
		||||
    return -1;
 | 
			
		||||
  }
 | 
			
		||||
  response[bytes_received] = '\0';
 | 
			
		||||
 | 
			
		||||
  // Unlock the socket
 | 
			
		||||
  pthread_mutex_unlock(&socket_mutex);
 | 
			
		||||
 | 
			
		||||
  // Close the client socket
 | 
			
		||||
  close(client_fd);
 | 
			
		||||
 | 
			
		||||
  // Check the response
 | 
			
		||||
  if (response[0] == 'a' && response[1] == 'y' && response[2] == '\0') {
 | 
			
		||||
    return 0; // Access granted
 | 
			
		||||
  } else if (response[0] == 'a' && response[1] == 'n' && response[2] == '\0') {
 | 
			
		||||
    return 1; // Access denied
 | 
			
		||||
  } else {
 | 
			
		||||
    // fprintf(stderr, "Invalid response from GUI: %s\n", response);
 | 
			
		||||
    return -1; // Invalid response
 | 
			
		||||
  }
 | 
			
		||||
}
 | 
			
		||||
@@ -6,14 +6,19 @@
 | 
			
		||||
#ifndef UI_SOCKET_H
 | 
			
		||||
#define UI_SOCKET_H
 | 
			
		||||
 | 
			
		||||
#include <sys/types.h>
 | 
			
		||||
 | 
			
		||||
struct process_info {
 | 
			
		||||
  // TODO: define some fields
 | 
			
		||||
  pid_t PID;
 | 
			
		||||
  const char *name;
 | 
			
		||||
  uid_t UID;
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
int init_ui_socket();
 | 
			
		||||
// For default socket location, set socket_path = NULL.
 | 
			
		||||
int init_ui_socket(const char *socket_path);
 | 
			
		||||
 | 
			
		||||
// TODO: design an interface for asking user for permission.
 | 
			
		||||
 | 
			
		||||
int ask_access(const char *filename, process_info pi);
 | 
			
		||||
int ask_access(const char *filename, struct process_info pi);
 | 
			
		||||
 | 
			
		||||
#endif // !UI_SOCKET_H
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user