jadesocket.c

/**
 * Jade Cheng
 * ICS 451
 * Assignment 1
 */

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/socket.h>
#include <netinet/in.h>
#include <netdb.h>
#include "jadesocket.h"

/**
 * This function loops and accepts socket connections on a specified port.  The
 * function calls the "fn" function when a connection is made.  If that function
 * returns a EXIT_FAILURE, this function returns.  Otherwise, it loops forever.
 *
 * @param s The socket descriptor.
 * @param buffer The stream of data to send.
 * @param count The maximum length to send.
 *
 * @return EXIT_SUCCESS if successful; EXIT_FAILURE if not.
 */
int js_accept_all(JS_ACCEPT_ALL_PROC fn, short port, int backlog)
{
    int                  passive;
    int                  session;
    struct sockaddr_in   sin;
    struct sockaddr    * sap;
    struct protoent    * protocolentry;
    socklen_t            adrsize;

    protocolentry = getprotobyname("tcp");
    if (protocolentry == NULL) {
        perror("getprotobyname");
        return EXIT_FAILURE;
    }

    passive = socket(PF_INET, SOCK_STREAM, protocolentry->p_proto);
    if (passive < 0) {
        perror("socket");
        return EXIT_FAILURE;
    }

    memset(&sin, 0, sizeof (sin));
    sin.sin_family      = AF_INET;
    sin.sin_port        = htons(port);
    sin.sin_addr.s_addr = INADDR_ANY;
    sap = (struct sockaddr *) &sin;
    if (bind(passive, sap, sizeof(sin)) != 0) {
        perror("bind");
        close(passive);
        return EXIT_FAILURE;
    }

    if (listen(passive, backlog) < 0) {
        perror("listen");
        close(passive);
        return EXIT_FAILURE;
    }

    adrsize = sizeof(sin);
    while ((session = accept(passive, sap, &adrsize)) >= 0) {
        if (EXIT_SUCCESS != fn(session)) {
            close(passive);
            return EXIT_FAILURE;
        }
    }

    close(passive);
    return EXIT_SUCCESS;
}

/**
 * This function sends data through the specified socket until the bytes sent
 * reaches the specified length.
 *
 * @param s The socket descriptor.
 * @param buffer The stream of data to send.
 * @param count The maximum length to send.
 *
 * @return EXIT_SUCCESS if successful; EXIT_FAILURE if not.
 */
int js_send(int s, const void * buffer, int count)
{
    while (count > 0) {
        int actual;

        actual = send(s, buffer, count, 0);

        if (actual <= 0) {
            fprintf(stderr, "Error on line %d in %s\n", __LINE__, __FILE__);
            return EXIT_FAILURE;
        }

        count -= actual;
    }

    return EXIT_SUCCESS;
}
Valid HTML 4.01 Valid CSS