Difference between revisions of "Peerd.c"

From Organic Design wiki
 
(move server code out to server.c)
Line 4: Line 4:
 
#include <stdio.h>
 
#include <stdio.h>
 
#include <string.h>
 
#include <string.h>
 
// Includes for socket (trying to use one source cpp for osx,win32,*ux)
 
#ifdef WINDOWS
 
#include <winsock.h>
 
#else
 
#include <sys/socket.h>
 
#include <netinet/in.h>
 
#include <arpa/inet.h>
 
#include <netdb.h>
 
#include <unistd.h>
 
#endif
 
 
// Socket
 
#define LISTENPORT 2012
 
#define BACKLOG 10
 
#define MSG "ow!"
 
  
 
// Nodes
 
// Nodes
Line 115: Line 99:
  
 
// SOCKET
 
// SOCKET
// - todo: don't exit on connect errors, keep trying every 10s
+
#include "server.c"
if (0) {
 
int sock, conn;
 
struct sockaddr_in my_addr, client_addr;
 
int sockopt_on = 1;
 
int sa_in_size = sizeof(struct sockaddr_in);
 
char response[80];
 
 
 
//get a socket
 
if ((sock = socket(PF_INET, SOCK_STREAM, IPPROTO_TCP)) == -1) {
 
perror("socket");
 
exit(1);
 
}
 
 
 
//make it reusable
 
if (setsockopt(sock,SOL_SOCKET,SO_REUSEADDR,&sockopt_on,sizeof(int)) == -1) {
 
perror("setsockopt");
 
exit(1);
 
}
 
 
 
//first zero the struct
 
memset((char *) &my_addr, 0, sa_in_size);
 
 
 
//now fill in the fields we need
 
my_addr.sin_family = PF_INET;
 
my_addr.sin_port = htons(LISTENPORT);
 
my_addr.sin_addr.s_addr = htonl(INADDR_ANY);
 
 
 
//bind our socket to the port
 
if (bind(sock,(struct sockaddr *)&my_addr, sa_in_size) == -1) {
 
perror("bind");
 
exit(1);
 
}
 
 
 
//start listening for incoming connections
 
if (listen(sock,BACKLOG) == -1) {
 
perror("listen");
 
exit(1);
 
}
 
 
 
while(1) {
 
//grab connections
 
conn = accept(sock, (struct sockaddr *)&client_addr, &sa_in_size);
 
if (conn == -1) {
 
  perror("accept");
 
  exit(1);
 
}
 
 
 
//log the connecter
 
printf("got connection from %s\n", inet_ntoa(client_addr.sin_addr));
 
 
 
//send a greeting
 
if (send(conn,MSG,strlen(MSG)+1,0) == -1) {
 
  perror("send");
 
}
 
 
 
//get the reply
 
if (recv(conn, &response, 80, 0) == -1) {
 
  perror("recv");
 
}
 
printf("The client says \"%s\"\n",&response);
 
close(conn);
 
 
 
}
 
}
 
 
 
 
 
  
 
// NODAL CONTENT - default "hardwired" default-nodal-app
 
// NODAL CONTENT - default "hardwired" default-nodal-app

Revision as of 10:56, 1 July 2006

// prototype of listSpace in c // Licenced under LGPL: www.gnu.org/copyleft/lesser.html

  1. include <stdlib.h>
  2. include <stdio.h>
  3. include <string.h>

// Nodes

  1. define CURRENT 2
  2. define AND 3
  3. define THEN 4
  4. define CODE 5

// Globals & constants

  1. define MAXITEMS 10000

int items = 0; int *space;

// Strucst used to emulate a variant-type typedef struct types { char* text; void (*code)(); int number; } variant;

int main() {

   #include "listSpace.c"

// NODE SPACE

int nodeTraverse(int subject, int path) { // select node wco selNode return subject; }

// set nodal value of node/path // - path is array-of-node int nodeGetValue(int subject, int path) { int value; return value; }

void nodeSetValue(int subject, int path, int value) { }

// PROBLEM: // - currently this code assumes all states are text, // but we need to be able to return function references too. // - not sure how to handle this in C++ properly, // we could get state to return a struct with STRING, INT, CODE // the caller knows which field is populated variant nodeGetState(int subject) { variant state; return state; }

void nodeSetState(int subject, variant state) { }

int nodeInsertKey(int subject, int key) { int instance; return instance; }

void nodeRemoveKey(int subject, int key) { }

// - Consumes quanta of execution // - Creates History from change events // - Builds, declares and executes functionality // - Should reduction handle cyles (current-cycle etc), or a separate root-thread void nodeReduce(int subject) { // return if no CURRENT node (either nonexistent, or ref to node 0) int node; if ((node = nodeGetValue(subject, CURRENT)) == 0) return; nodeSetValue(subject, CURRENT, nodeGetValue(node, AND)); if (nodeGetValue(node, CODE)) { void (*code)() = nodeGetState(node).code; code(); // Later this must declare and build if no function-reference // replace self in loop with node.THEN if non-zero } else nodeReduce(node); }


// MAIN

int i,j; // global iterators

// Allocate memory for maximum ListItems space = calloc(MAXITEMS*3, sizeof(int)); printf("%d bytes of memory allocated\n", MAXITEMS*3*sizeof(int));

// Insert items 0-127 as ascii character nodes // - this allows us to temporarily use list-space as a dictionary // since C/C++ doesn't inherently have one for (i=0; i<128; i++) listInsert();


// SOCKET

  1. include "server.c"

// NODAL CONTENT - default "hardwired" default-nodal-app

// define the serialsed-text version of nodal structure // - allow shorthand for Next's?

// NodalSpace = deserialise(string);

// if the node is a function (same type-check as reduce() uses), // then use its value (if any) as local function name, // change it to a ref with this[functionName] (if pre-declared - see below)


// NODAL FUNCTIONS - later included in content instead of "hardwired" here

// pre-declared functions built by nodal-app // Currently it can't compile, so additional functionality required by nodal-app are pre-declared here // later the script and its functions will be a nodal-state produced by a nodal-build and cache

// Process passed "alias1|alias2|alias3..." string (GUID's are just alias's) // NOTE: GUID-alias is traversed as ASCII not binary - these are external guids // - this is using list-space as a dictionary // - the nodal structure of a number can still be binary // - used by [de]serialise() // - returns integer index of subject node int processNodeLink(char *link) { int subject = atoi(link); // not like this anymore, passed link is external // - split by pipe and for each, // - if its a number, convert to a binary-coded-string of \x00's and \x01's // - traverse from root through name using chr-as-node-index, // - the first iteration creates the subject, // - subsequent iterations must link their last jump to the existing subject return subject; }

// Treat each character in text as a list-item-index to traverse from root int traverseText(char *text) { int i,subject = 0; for (i=0; i<strlen(text); i++) subject = listTraverse(subject, (int)text[i]); return subject; }

// Convert a node to text for storage or transport char* serialise(int subject) { char *text; return text; }

// Convert textual represntation of one or more nodes and associations to nodal change int deserialise(char *text) { printf("\nPARSING THE FOLLOWING TEXT:\n--------------------------------------------\n%s\n--------------------------------------------\n\n", text); printf("INFORMATION EXTRACTED:\n--------------------------------------------\n"); int node, subject = 0, key, i, j = 0, linkStart, c; char links[100]; char *link1 = (char*)&links; char *link2 = link1+50; for (i = 0; i < strlen(text); i++) { char *s = text+i; if ((c = (int)s[0]) < 32) j = 1; else switch (j) { case 0: // waiting for next line break; case 1: // starting new line // - if not starting with *[[ then wait for next line if (strncmp(s, "*[[", 3) == 0) { j = 2; linkStart = i; } else j = 0; break; case 2: // processing first link if (strncmp(s, "]]", 2) == 0) { if (strncmp(s, "]]:[[", 5) == 0) { // link1 as an association-key // key = strtoint(...) j = 3; // process link2 next } else { // link1 specifies a change of nodal subject link1 = strncpy(link1, text+linkStart+3, i-linkStart-3); link1[i-linkStart-3] = '\0'; subject = processNodeLink(link1); printf("%d:\n", subject); j = 0; // wait for new line } } break; case 3: // processing second link if (strncmp(s, "]]", 2) == 0) { // process link2 link1 = strncpy(link1, text+linkStart+3, i-linkStart-3); link2 = strchr(link1, '[')+2; link1[i-linkStart-3] = '\0'; link1[i-linkStart-strlen(link2)-8] = '\0'; int key = processNodeLink(link1); int val = processNodeLink(link2); // store in nodal-space // - we use list functions because nodal functions cause change listSetValue(listTraverse(subject,key),val); printf("  %d => %d\n", key, val); j = 0; } break; } //printf("chr:%c,%d\n",s[0],j); } printf("--------------------------------------------\n"); return node; }

// box properties // events // tcc

int test = deserialise( "testing deserialise:\n\r== can do headings for wiki ==\n*Foo\n*bar:hello # my special association\r\r\n*baz:world\n*key:1628\n*key2:[[8928|]]\n*key3:value"); printf("\n%d list-space items have been created.\n", items);

// Count how many nodes have payloads int p=0; for (i=0; i<MAXITEMS; i++) if (listGetValue(i)) p++; printf("%d items in use:\n", p); for (i=0; i<MAXITEMS; i++) if (j=listGetValue(i)) printf("  %d = %d\n",i,j); printf("\n\n");

}