WIP: ready to work

This commit is contained in:
Adrien Bourmault 2024-03-13 20:10:10 +02:00
parent efd547c85d
commit 4214fc2502
Signed by: neox
GPG Key ID: 95F65F55F682A17A
17 changed files with 995 additions and 329 deletions

2
.gitignore vendored
View File

@ -2,3 +2,5 @@
*.o *.o
*.deb *.deb
bin/** bin/**
build/**

View File

@ -39,10 +39,11 @@ NTHREADS= $(shell nproc)
CC=gcc CC=gcc
WARNINGS= -Wall WARNINGS= -Wall
DEBUG= -ggdb -fno-omit-frame-pointer -fdiagnostics-color=always -fsanitize=bounds -fstack-check DEBUG= -ggdb -fno-omit-frame-pointer -fdiagnostics-color=always \
#-fsanitize=address \ -fsanitize=bounds -fstack-check -fopenmp \
#-fsanitize=pointer-compare -fsanitize=pointer-subtract \ -fsanitize=address \
#-fsanitize=leak -fsanitize=undefined -fsanitize=null -fsanitize=bounds -fsanitize=pointer-compare -fsanitize=pointer-subtract \
-fsanitize=leak -fsanitize=undefined -fsanitize=null -fsanitize=bounds
OPTIMIZE= -O3 OPTIMIZE= -O3
INCLUDE= $(shell pkg-config --cflags glib-2.0 libxml-2.0 gtk4) INCLUDE= $(shell pkg-config --cflags glib-2.0 libxml-2.0 gtk4)
LIBS= $(shell pkg-config --libs glib-2.0 libxml-2.0 gtk4) -lGL -lGLU -lm -lepoxy -lX11 -lGLEW LIBS= $(shell pkg-config --libs glib-2.0 libxml-2.0 gtk4) -lGL -lGLU -lm -lepoxy -lX11 -lGLEW
@ -112,8 +113,7 @@ build_system:
run: build_system run: build_system
@echo -e ${CL2}[$@] ${CL}executing...${CL3} @echo -e ${CL2}[$@] ${CL}executing...${CL3}
@gdb bin/gem-graph-server \ @bin/gem-graph-server -C data/config -M data/models -U data/users
-ex "set args -C debian/etc -M debian/var/models -U debian/var/users"
@echo -e ${CL2}[$@] ${CL}done.${CL3} @echo -e ${CL2}[$@] ${CL}done.${CL3}
debug: build_system debug: build_system
@ -124,19 +124,17 @@ debug: build_system
valgrind: build_system valgrind: build_system
@echo -e ${CL2}[$@] ${CL}executing...${CL3} @echo -e ${CL2}[$@] ${CL}executing...${CL3}
@valgrind --leak-check=full --show-leak-kinds=all -s \ @valgrind --leak-check=full --show-leak-kinds=all -s \
bin/gem-graph-server -C debian/etc -M debian/var/models \ bin/gem-graph-server -C data/config -M data/models -U data/users
-U debian/var/users
@echo -e ${CL2}[$@] ${CL}done.${CL3} @echo -e ${CL2}[$@] ${CL}done.${CL3}
run-both: build_system run-both: build_system
@echo -e ${CL2}[$@] ${CL}executing...${CL3} @echo -e ${CL2}[$@] ${CL}executing...${CL3}
@bin/gem-graph-server -C debian/etc -M debian/var/models \ @bin/gem-graph-server -C data/config -M data/models -U data/users\
-U debian/var/users & sleep 1 && bin/gem-graph-ctl & sleep 1 && bin/gem-graph-ctl
@echo -e ${CL2}[$@] ${CL}done.${CL3} @echo -e ${CL2}[$@] ${CL}done.${CL3}
run-server: build_system run-server: build_system
@echo -e ${CL2}[$@] ${CL}executing...${CL3} @echo -e ${CL2}[$@] ${CL}executing...${CL3}
@bin/gem-graph-server -C debian/etc -M debian/var/models \ @bin/gem-graph-server -C data/config -M data/models -U data/users
-U debian/var/users
@echo -e ${CL2}[$@] ${CL}done.${CL3} @echo -e ${CL2}[$@] ${CL}done.${CL3}
all: build_system all: build_system

View File

@ -0,0 +1,118 @@
<?xml version="1.0" encoding="UTF-8"?>
<gem-graph-model version="0.2.1">
<identity>
<name>Modèle de test</name>
<owner>Léontine Patinette</owner>
<owner_id>2</owner_id>
<date>1630000000</date>
<version>1.0</version>
<g_ref id="Cause" date="1630000000" author="toujours" lang="en">Ref</g_ref>
</identity>
<parameters id="texte" date="0" author="Léontine Trottine.">
<simulation>
<max_thread>0</max_thread>
<max_cycles>9</max_cycles>
</simulation>
<space-param>
<!-- loop_on_zero="true" anything moved before zero reenters at the end of space-->
<!-- loop_on_zero="false" anything moved before zero is lost-->
<!-- loop_on_max="true" anything moved beyond max reenters at the zero of space-->
<!-- loop_on_max="false" anything moved beyond max is lost-->
<dimension x="29"/>
<!-- Site_multiplicity = number of sites in a space unit. -->
<!-- Each site points towards a neighbouring space unit. -->
<!-- Several arrows can be stacked in the same site. -->
<site_multiplicity>3</site_multiplicity>
</space-param>
</parameters>
<!-- Model objects definition -->
<objects id="only dimers in this model" date="1630000000" author="inanimés,... âme ?">
<object id="a dimer" date="1630000000" author="Alphonse">
<arrow site="1" weight="1" x="0"/>
<arrow site="2" weight="1" x="1"/>
</object>
</objects>
<!-- Saved space description (initial space is sequence 0) -->
<savedstates id="texte" date="1630000000" author="Qui courrait dans l'herbe'">
<state id="initial" date="1630000000" author="Une souris verte">
<arrow site="0" weight="1" x="0"/>
<arrow site="1" weight="1" x="1"/>
<arrow site="0" weight="1" x="10"/>
<arrow site="1" weight="1" x="11"/>
<arrow site="0" weight="1" x="20"/>
<arrow site="1" weight="1" x="21"/>
<!-- Three dimers 1-1 are drawn in the global space
at locations (0,1) (10,11) and (20,21) -->
</state>
</savedstates>
<!-- Model transitions definition (rules) -->
<!-- In this version : <xs:sequence minOccurs="0" maxOccurs="unbounded">-->
<!-- Transitions should be edited by hand and written in a 'human-readable' format -->
<conditions id="random walk of dimers" date="1630000000" author="Zazard le lézard !">
<condition site="1" weight="1" node_id="1" parent="0" x="0"/>
<condition site="2" weight="1" node_id="2" parent="1" x="1"/>
<!-- as soon as conditions 1 and 2 are satisfied, a dimer is identified at atation (0,1). -->
<condition site="1" weight="0" node_id="3" parent="2" x="2"/>
<!-- as soon as condition 3 is satisfied,
the neighbouring space unit to East of the dimer is empty
and the dimer identified by conditions (1,2) can be moved to East. -->
<condition site="2" weight="0" node_id="4" parent="2" x="-1"/>
<!-- as soon as condition 4 is satisfied,
the neighbouring space unit to West of the dimer is empty
and the dimer identified by conditions (1,2) can be moved to West. -->
</conditions>
<transitions>
<transition id="move_a_dimer_to_east" date="1630000000" author="Pas moi..."
parent="3" probability="1">
<arrow site="1" weight="0" x="0"/>
<arrow site="2" weight="0" x="1"/>
<arrow site="1" weight="1" x="1"/>
<arrow site="2" weight="1" x="2"/>
</transition>
<transition id="move_a_dimer_to_west" date="1630000000" author="Ni moi !"
parent="4" probability="1">
<arrow site="1" weight="0" x="0"/>
<arrow site="2" weight="0" x="1"/>
<arrow site="2" weight="1" x="0"/>
<arrow site="1" weight="1" x="1"/>
</transition>
</transitions>
</gem-graph-model>

View File

@ -0,0 +1,145 @@
<?xml version="1.0" encoding="UTF-8"?>
<gem-graph-model version="0.2.1">
<identity>
<name>Test 21-03-2023</name>
<owner>J</owner>
<owner_id>J</owner_id>
<date>time_stamp</date>
<version>1.0</version>
<g_ref id="Cause" date="time_stamp" author="J" lang="en">Ref</g_ref>
</identity>
<parameters id="texte" date="0" author="J">
<simulation>
<max_thread>0</max_thread>
<max_cycles>9</max_cycles>
</simulation>
<space-param>
<!-- loop_on_zero="true" anything moved before zero reenters at the end of space-->
<!-- loop_on_zero="false" anything moved before zero is lost-->
<!-- loop_on_max="true" anything moved beyond max reenters at the zero of space-->
<!-- loop_on_max="false" anything moved beyond max is lost-->
<dimension x="22" y="4" z="8"/>
<!-- Site_multiplicity = number of sites in a space unit. -->
<!-- Each site points towards a neighbouring space unit. -->
<!-- Several arrows can be stacked in the same site. -->
<site_multiplicity>3</site_multiplicity>
</space-param>
</parameters>
<!-- Model objects definition -->
<objects id="only dimers in this model" date="time_stamp" author="J">
<object id="a dimer" date="time_stamp" author="J">
<arrow site="1" weight="1" x="0"/>
<arrow site="2" weight="1" x="1"/>
</object>
</objects>
<!-- Saved space description (initial space is sequence 0) -->
<savedstates id="texte" date="time_stamp" author="J">
<state id="initial" date="time_stamp" author="J">
<arrow site="1" weight="1" x="0"/>
<arrow site="2" weight="1" x="1"/>
<arrow site="1" weight="1" x="10"/>
<arrow site="2" weight="1" x="11"/>
<arrow site="1" weight="1" x="20"/>
<arrow site="2" weight="1" x="21"/>
<!-- Three dimers 1-1 are drawn in the global space
at locations (0,1) (10,11) and (20,21) -->
</state>
</savedstates>
<!-- Model transitions definition (rules) -->
<!-- In this version : <xs:sequence minOccurs="0" maxOccurs="unbounded">-->
<!-- Transitions should be edited by hand and written in a 'human-readable' format -->
<conditions_tree>
<condition_anonym site="1" weight="1" x="0">
<condition_anonym site="2" weight="1" x="1">
<condition_anonym site="1" weight="0" x="2">
<transition_anonym id="move_a_dimer_to_east"
date="time_stamp"
author="J"
probability="0.5"/>
<arrow site="1" weight="0" x="0"/>
<arrow site="2" weight="0" x="1"/>
<arrow site="1" weight="1" x="1"/>
<arrow site="2" weight="1" x="2"/>
</condition_anonym>
<condition_anonym site="2" weight="0" x="-1">
<transition_anonym id="move_a_dimer_to_west"
date="time_stamp"
author="J"
probability="0.5"/>
<arrow site="1" weight="0" x="0"/>
<arrow site="2" weight="0" x="1"/>
<arrow site="2" weight="1" x="0"/>
<arrow site="1" weight="1" x="1"/>
</condition_anonym>
</condition_anonym>
</condition_anonym>
</conditions_tree>
<conditionslist id="random walk of dimers" date="time_stamp" author="J">
<condition site="1" weight="1" node_id="1" parent="0" x="0"/>
<condition site="2" weight="1" node_id="2" parent="1" x="1"/>
<!-- as soon as conditions 1 and 2 are satisfied, a dimer is identified at atation (0,1). -->
<condition site="1" weight="0" node_id="3" parent="2" x="2"/>
<!-- as soon as condition 3 is satisfied,
the neighbouring space unit to East of the dimer is empty
and the dimer identified by conditions (1,2) can be moved to East. -->
<condition site="2" weight="0" node_id="4" parent="2" x="-1"/>
<!-- as soon as condition 4 is satisfied,
the neighbouring space unit to West of the dimer is empty
and the dimer identified by conditions (1,2) can be moved to West. -->
</conditionslist>
<transitionslist>
<transition id="move_a_dimer_to_east" date="time_stamp" author="J"
parent="3" probability="1">
<arrow site="1" weight="0" x="0"/>
<arrow site="2" weight="0" x="1"/>
<arrow site="1" weight="1" x="1"/>
<arrow site="2" weight="1" x="2"/>
</transition>
<transition id="move_a_dimer_to_west" date="time_stamp" author="J"
parent="4" probability="1">
<arrow site="1" weight="0" x="0"/>
<arrow site="2" weight="0" x="1"/>
<arrow site="2" weight="1" x="0"/>
<arrow site="1" weight="1" x="1"/>
</transition>
</transitionslist>
</gem-graph-model>

View File

@ -0,0 +1,194 @@
<?xml version="1.0" encoding="UTF-8"?>
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema">
<!-- https://www.freeformatter.com/xml-validator-xsd.html -->
<xs:attribute name="id" type="xs:string"/>
<xs:attribute name="node_id" type="xs:integer"/>
<xs:attribute name="parent" type="xs:integer"/>
<xs:attribute name="date" type="xs:integer"/>
<xs:attribute name="name" type="xs:string"/>
<xs:attribute name="lang" type="xs:string"/>
<xs:attribute name="owner" type="xs:string"/>
<xs:attribute name="owner_id" type="xs:integer"/>
<xs:attribute name="author" type="xs:string"/>
<xs:attribute name="version" type="xs:float"/>
<xs:attribute name="probability" type="xs:integer"/>
<xs:attribute name="site" type="xs:integer" default="0"/>
<xs:attribute name="weight" type="xs:integer" default="0"/>
<xs:attribute name="u" type="xs:integer"/>
<xs:attribute name="v" type="xs:integer"/>
<xs:attribute name="w" type="xs:integer"/>
<xs:attribute name="x" type="xs:integer"/>
<xs:attribute name="y" type="xs:integer"/>
<xs:attribute name="z" type="xs:integer"/>
<xs:attribute name="t" type="xs:integer"/>
<xs:attributeGroup name="id_date_author">
<xs:attribute ref="id"/>
<xs:attribute ref="date"/>
<xs:attribute ref="author"/>
</xs:attributeGroup>
<xs:element name="g_ref">
<xs:complexType>
<xs:simpleContent>
<xs:extension base="xs:string">
<xs:attributeGroup ref="id_date_author"/>
<xs:attribute ref="lang" use="required"/>
</xs:extension>
</xs:simpleContent>
</xs:complexType>
</xs:element>
<xs:element name="quote" substitutionGroup="g_ref"/>
<xs:element name="dimension">
<xs:complexType>
<xs:attribute ref="u" use="optional"/>
<xs:attribute ref="v" use="optional"/>
<xs:attribute ref="w" use="optional"/>
<xs:attribute ref="x" use="optional"/>
<xs:attribute ref="y" use="optional"/>
<xs:attribute ref="z" use="optional"/>
<xs:attribute ref="t" use="optional"/>
</xs:complexType>
</xs:element>
<xs:element name="arrow">
<xs:complexType>
<xs:attribute ref="site" use="required"/>
<xs:attribute ref="weight" use="required"/>
<xs:attribute ref="u" use="optional"/>
<xs:attribute ref="v" use="optional"/>
<xs:attribute ref="w" use="optional"/>
<xs:attribute ref="x" use="optional"/>
<xs:attribute ref="y" use="optional"/>
<xs:attribute ref="z" use="optional"/>
<xs:attribute ref="t" use="optional"/>
</xs:complexType>
</xs:element>
<xs:element name="condition">
<xs:complexType>
<xs:attribute ref="site" use="required"/>
<xs:attribute ref="weight" use="required"/>
<xs:attribute ref="node_id" use="required"/>
<xs:attribute ref="parent" use="required"/>
<xs:attribute ref="u" use="optional"/>
<xs:attribute ref="v" use="optional"/>
<xs:attribute ref="w" use="optional"/>
<xs:attribute ref="x" use="optional"/>
<xs:attribute ref="y" use="optional"/>
<xs:attribute ref="z" use="optional"/>
<xs:attribute ref="t" use="optional"/>
</xs:complexType>
</xs:element>
<xs:element name="state">
<xs:complexType>
<xs:sequence minOccurs="1" maxOccurs="unbounded">
<xs:element ref="arrow"/>
</xs:sequence>
<xs:attributeGroup ref="id_date_author"/>
</xs:complexType>
</xs:element>
<xs:element name="object" substitutionGroup="state"/>
<xs:element name="transition">
<xs:complexType>
<xs:sequence minOccurs="1" maxOccurs="unbounded">
<xs:element minOccurs="0" ref="quote"/>
<xs:element ref="arrow"/>
</xs:sequence>
<xs:attributeGroup ref="id_date_author"/>
<xs:attribute ref="parent" use="required"/>
<xs:attribute ref="probability" use="required"/>
</xs:complexType>
</xs:element>
<xs:element name="gem-graph-model">
<xs:complexType>
<xs:sequence minOccurs="1" maxOccurs="1">
<xs:element name="identity">
<xs:complexType>
<xs:sequence minOccurs="1" maxOccurs="1">
<xs:element name="name" type="xs:string"/>
<xs:element name="owner" type="xs:string"/>
<xs:element name="owner_id" type="xs:integer"/>
<xs:element name="date" type="xs:integer"/>
<xs:element name="version" type="xs:float"/>
<xs:element ref="g_ref" minOccurs="1" maxOccurs="1"/>
</xs:sequence>
</xs:complexType>
</xs:element>
<xs:element name="parameters">
<xs:complexType>
<xs:sequence minOccurs="1" maxOccurs="1">
<xs:element name="simulation">
<xs:complexType>
<xs:sequence minOccurs="1" maxOccurs="1">
<xs:element name="max_thread" type="xs:integer"/>
<xs:element name="max_cycles" type="xs:integer"/>
</xs:sequence>
</xs:complexType>
</xs:element>
<xs:element name="space-param">
<xs:complexType>
<xs:sequence minOccurs="1" maxOccurs="1">
<xs:element ref="dimension"/>
<xs:element name="site_multiplicity" type="xs:integer"/>
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:sequence>
<xs:attributeGroup ref="id_date_author"/>
</xs:complexType>
</xs:element>
<xs:element name="objects">
<xs:complexType>
<xs:sequence minOccurs="1" maxOccurs="unbounded">
<xs:element ref="object"/>
</xs:sequence>
<xs:attributeGroup ref="id_date_author"/>
</xs:complexType>
</xs:element>
<xs:element name="savedstates">
<xs:complexType>
<xs:sequence minOccurs="0" maxOccurs="unbounded">
<xs:element ref="state"/>
</xs:sequence>
<xs:attributeGroup ref="id_date_author"/>
</xs:complexType>
</xs:element>
<xs:element name="conditions">
<xs:complexType>
<xs:sequence minOccurs="0" maxOccurs="unbounded">
<xs:element minOccurs="0" ref="quote"/>
<xs:element ref="condition"/>
</xs:sequence>
<xs:attributeGroup ref="id_date_author"/>
</xs:complexType>
</xs:element>
<xs:element name="transitions">
<xs:complexType>
<xs:sequence minOccurs="0" maxOccurs="unbounded">
<xs:element ref="transition"/>
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:sequence>
<xs:attribute ref="version" use="required"/>
</xs:complexType>
</xs:element>
</xs:schema>

View File

@ -0,0 +1,235 @@
<?xml version="1.0" encoding="UTF-8"?>
<xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema">
<!-- https://www.freeformatter.com/xml-validator-xsd.html -->
<xs:attribute name="id" type="xs:string"/>
<xs:attribute name="node_id" type="xs:integer"/>
<xs:attribute name="parent" type="xs:integer"/>
<xs:attribute name="date" type="xs:integer"/>
<xs:attribute name="name" type="xs:string"/>
<xs:attribute name="lang" type="xs:string"/>
<xs:attribute name="owner" type="xs:string"/>
<xs:attribute name="owner_id" type="xs:integer"/>
<xs:attribute name="author" type="xs:string"/>
<xs:attribute name="version" type="xs:float"/>
<xs:attribute name="probability" type="xs:integer"/>
<xs:attribute name="site" type="xs:integer" default="0"/>
<xs:attribute name="weight" type="xs:integer" default="0"/>
<xs:attribute name="u" type="xs:integer"/>
<xs:attribute name="v" type="xs:integer"/>
<xs:attribute name="w" type="xs:integer"/>
<xs:attribute name="x" type="xs:integer"/>
<xs:attribute name="y" type="xs:integer"/>
<xs:attribute name="z" type="xs:integer"/>
<xs:attribute name="t" type="xs:integer"/>
<xs:attributeGroup name="id_date_author">
<xs:attribute ref="id"/>
<xs:attribute ref="date"/>
<xs:attribute ref="author"/>
</xs:attributeGroup>
<xs:element name="g_ref">
<xs:complexType>
<xs:simpleContent>
<xs:extension base="xs:string">
<xs:attributeGroup ref="id_date_author"/>
<xs:attribute ref="lang" use="required"/>
</xs:extension>
</xs:simpleContent>
</xs:complexType>
</xs:element>
<xs:element name="quote" substitutionGroup="g_ref"/>
<xs:element name="dimension">
<xs:complexType>
<xs:attribute ref="u" use="optional"/>
<xs:attribute ref="v" use="optional"/>
<xs:attribute ref="w" use="optional"/>
<xs:attribute ref="x" use="optional"/>
<xs:attribute ref="y" use="optional"/>
<xs:attribute ref="z" use="optional"/>
<xs:attribute ref="t" use="optional"/>
</xs:complexType>
</xs:element>
<xs:element name="arrow">
<xs:complexType>
<xs:attribute ref="site" use="required"/>
<xs:attribute ref="weight" use="required"/>
<xs:attribute ref="u" use="optional"/>
<xs:attribute ref="v" use="optional"/>
<xs:attribute ref="w" use="optional"/>
<xs:attribute ref="x" use="required"/>
<xs:attribute ref="y" use="optional"/>
<xs:attribute ref="z" use="optional"/>
<xs:attribute ref="t" use="optional"/>
</xs:complexType>
</xs:element>
<xs:element name="condition">
<xs:complexType>
<xs:attribute ref="site" use="required"/>
<xs:attribute ref="weight" use="required"/>
<xs:attribute ref="node_id" use="required"/>
<xs:attribute ref="parent" use="required"/>
<xs:attribute ref="u" use="optional"/>
<xs:attribute ref="v" use="optional"/>
<xs:attribute ref="w" use="optional"/>
<xs:attribute ref="x" use="required"/>
<xs:attribute ref="y" use="optional"/>
<xs:attribute ref="z" use="optional"/>
<xs:attribute ref="t" use="optional"/>
</xs:complexType>
</xs:element>
<xs:element name="condition_anonym">
<xs:complexType>
<xs:sequence minOccurs="0" maxOccurs="unbounded">
<xs:element ref="condition_anonym"/>
</xs:sequence>
<xs:sequence minOccurs="0" maxOccurs="unbounded">
<xs:element ref="arrow"/>
</xs:sequence>
<xs:attribute ref="site" use="required"/>
<xs:attribute ref="weight" use="required"/>
<xs:attribute ref="u" use="optional"/>
<xs:attribute ref="v" use="optional"/>
<xs:attribute ref="w" use="optional"/>
<xs:attribute ref="x" use="required"/>
<xs:attribute ref="y" use="optional"/>
<xs:attribute ref="z" use="optional"/>
<xs:attribute ref="t" use="optional"/>
</xs:complexType>
</xs:element>
<xs:element name="state">
<xs:complexType>
<xs:sequence minOccurs="1" maxOccurs="unbounded">
<xs:element ref="arrow"/>
</xs:sequence>
<xs:attributeGroup ref="id_date_author"/>
</xs:complexType>
</xs:element>
<xs:element name="object" substitutionGroup="state"/>
<xs:element name="transition">
<xs:complexType>
<xs:sequence minOccurs="1" maxOccurs="unbounded">
<xs:element minOccurs="0" ref="quote"/>
<xs:element ref="arrow"/>
</xs:sequence>
<xs:attributeGroup ref="id_date_author"/>
<xs:attribute ref="parent" use="required"/>
<xs:attribute ref="probability" use="required"/>
</xs:complexType>
</xs:element>
<xs:element name="transition_anonym">
<xs:complexType>
<xs:attributeGroup ref="id_date_author"/>
<xs:attribute ref="probability" use="required"/>
</xs:complexType>
</xs:element>
<xs:element name="gem-graph-model">
<xs:complexType>
<xs:sequence minOccurs="1" maxOccurs="1">
<xs:element name="identity">
<xs:complexType>
<xs:sequence minOccurs="1" maxOccurs="1">
<xs:element name="name" type="xs:string"/>
<xs:element name="owner" type="xs:string"/>
<xs:element name="owner_id" type="xs:integer"/>
<xs:element name="date" type="xs:integer"/>
<xs:element name="version" type="xs:float"/>
<xs:element ref="g_ref" minOccurs="1" maxOccurs="1"/>
</xs:sequence>
</xs:complexType>
</xs:element>
<xs:element name="parameters">
<xs:complexType>
<xs:sequence minOccurs="1" maxOccurs="1">
<xs:element name="simulation">
<xs:complexType>
<xs:sequence minOccurs="1" maxOccurs="1">
<xs:element name="max_thread" type="xs:integer"/>
<xs:element name="max_cycles" type="xs:integer"/>
</xs:sequence>
</xs:complexType>
</xs:element>
<xs:element name="space-param">
<xs:complexType>
<xs:sequence minOccurs="1" maxOccurs="1">
<xs:element ref="dimension"/>
<xs:element name="site_multiplicity" type="xs:integer"/>
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:sequence>
<xs:attributeGroup ref="id_date_author"/>
</xs:complexType>
</xs:element>
<xs:element name="objects">
<xs:complexType>
<xs:sequence minOccurs="1" maxOccurs="unbounded">
<xs:element ref="object"/>
</xs:sequence>
<xs:attributeGroup ref="id_date_author"/>
</xs:complexType>
</xs:element>
<xs:element name="savedstates">
<xs:complexType>
<xs:sequence minOccurs="0" maxOccurs="unbounded">
<xs:element ref="state"/>
</xs:sequence>
<xs:attributeGroup ref="id_date_author"/>
</xs:complexType>
</xs:element>
<xs:element name="conditionslist">
<xs:complexType>
<xs:sequence minOccurs="0" maxOccurs="unbounded">
<xs:element minOccurs="0" ref="quote"/>
<xs:element ref="condition"/>
</xs:sequence>
<xs:attributeGroup ref="id_date_author"/>
</xs:complexType>
</xs:element>
<xs:element name="transitionslist">
<xs:complexType>
<xs:sequence minOccurs="0" maxOccurs="unbounded">
<xs:element ref="transition"/>
</xs:sequence>
</xs:complexType>
</xs:element>
<xs:element name="conditionstree">
<xs:complexType>
<xs:sequence minOccurs="0" maxOccurs="unbounded">
<xs:element ref="condition_anonym"/>
</xs:sequence>
<xs:sequence minOccurs="0" maxOccurs="1">
<xs:element ref="transition_anonym"/>
</xs:sequence>
<xs:sequence minOccurs="0" maxOccurs="unbounded">
<xs:element ref="arrow"/>
</xs:sequence>
</xs:complexType>
</xs:element>
</xs:sequence>
<xs:attribute ref="version" use="required"/>
</xs:complexType>
</xs:element>
</xs:schema>

View File

@ -23,6 +23,7 @@
#include <sys/param.h> #include <sys/param.h>
#include <stdbool.h> #include <stdbool.h>
#include <pthread.h> #include <pthread.h>
#include <assert.h>
#include <unistd.h> #include <unistd.h>
#include <malloc.h> #include <malloc.h>
#include <string.h> #include <string.h>
@ -35,13 +36,29 @@
/* -------------------------------------------------------------------------- */ /* -------------------------------------------------------------------------- */
#define LOGMSG "[%s]" #define LOGMSG "<%s:%s()>"
#define printLog(FORMAT, ...) printf("\e[0m" LOGMSG " " FORMAT "\e[0m", \ #define printlog(FORMAT, ...) printf("\e[0m" LOGMSG " " FORMAT "\e[0m", \
__func__, ##__VA_ARGS__) __FILE__,__func__, ##__VA_ARGS__)
#define printErr(FORMAT,...) fprintf(stderr, "\e[0m" LOGMSG " " FORMAT "\e[0m",\ #define printerr(FORMAT,...) fprintf(stderr, "\e[0m" LOGMSG " " FORMAT "\e[0m",\
__func__, ##__VA_ARGS__) __FILE__,__func__, ##__VA_ARGS__)
#define LEN(x) (sizeof(x) / sizeof((x)[0])) #define LEN(x) (sizeof(x) / sizeof((x)[0]))
/* -------------------------------------------------------------------------- */ /* -------------------------------------------------------------------------- */
struct parameters_t
{
char *configDir;
char *userDir;
char *modelDir;
};
/*
* Structure describing an arrow
*/
struct arrow_t {
uint load;
uint site;
uint x;
uint y;
uint z;
};

View File

@ -32,26 +32,26 @@
/* -------------------------------------------------------------------------- */ /* -------------------------------------------------------------------------- */
struct command_t { // struct command_t {
const char *name; // const char *name;
char* (*execute)(char*, char**, Server_t*); // char* (*execute)(char*, char**, Server_t*);
const char *help; // const char *help;
} typedef command_t; // } typedef command_t;
/* -------------------------------------------------------------------------- */ /* -------------------------------------------------------------------------- */
// //
// Existing commands // Existing commands
// //
char *Cmd_model(char*, char**, Server_t*); // char *Cmd_model(char*, char**, Server_t*);
char *cmd_shutdown(char*, char**, Server_t*); // char *cmd_shutdown(char*, char**, Server_t*);
char *cmd_help(char*, char**, Server_t*); // char *cmd_help(char*, char**, Server_t*);
static command_t cmdList[] = // static command_t cmdList[] =
{ // {
{"help", cmd_help, "Help command"}, // {"help", cmd_help, "Help command"},
{"model", cmd_model, "Model command"}, // {"model", cmd_model, "Model command"},
{"shutdown", cmd_shutdown, "Shutdown command"}, // {"shutdown", cmd_shutdown, "Shutdown command"},
}; // };
/* -------------------------------------------------------------------------- */ /* -------------------------------------------------------------------------- */

View File

@ -29,8 +29,8 @@
#include <signal.h> #include <signal.h>
#include <string.h> #include <string.h>
#include <stdlib.h> #include <stdlib.h>
#include <libxml2/libxml/xmlmemory.h> #include <libxml/parser.h>
#include <libxml2/libxml/parser.h> #include <libxml/xmlschemas.h>
/* -------------------------------------------------------------------------- */ /* -------------------------------------------------------------------------- */
@ -51,44 +51,44 @@
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
// Model init function (and model discovery) // // Model init function (and model discovery) //
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
void model_system_init (parameters_t *parameters); // void model_system_init (parameters_t *parameters);
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
// Model stopping function // // Model stopping function //
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
void model_system_shutdown (void); // void model_system_shutdown (void);
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
// Load a model ready to execute // // Load a model ready to execute //
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
int model_load (int id); // int model_load (int id);
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
// Unload a model // // Unload a model //
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
int model_unload (int id); // int model_unload (int id);
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
// Add a model to the known model list // // Add a model to the known model list //
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
void model_add_to_known (model_t **newModel); // void model_add_to_known (model_t **newModel);
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
// Print informations about all models (known and loaded) to the client // // Print informations about all models (known and loaded) to the client //
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
void print_models (char *buf); // void print_models (char *buf);
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
// Launch a model execution // // Launch a model execution //
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
int model_run (int id); // int model_run (int id);
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
// Stop a model execution // // Stop a model execution //
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
int model_stop (int id); // int model_stop (int id);
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
// Stop and unload all loaded or running model // // Stop and unload all loaded or running model //
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
void model_shutdown (void); // void model_shutdown (void);

View File

@ -1,39 +0,0 @@
//=-------------------------------------------------------------------------=//
// XML parsing module //
// //
// Copyright © 2021 Libre en Communs (contact@a-lec.org) //
// Copyright © 2021 Adrien Bourmault (neox@a-lec.org) //
// //
// This file is part of gem-graph. //
// //
// This program is free software: you can redistribute it and/or modify //
// it under the terms of the GNU Affero General Public License as //
// published by the Free Software Foundation, either version 3 of the //
// License, or (at your option) any later version. //
// //
// This program is distributed in the hope that it will be useful, //
// but WITHOUT ANY WARRANTY; without even the implied warranty of //
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the //
// GNU Affero General Public License for more details. //
// //
// You should have received a copy of the GNU Affero General Public License //
// along with this program. If not, see <https://www.gnu.org/licenses/>. //
//=-------------------------------------------------------------------------=//
#pragma once
#ifndef BASE_H
#include "../include/base.h"
#endif
#include <string.h>
#include <stdlib.h>
#include <libxml/parser.h>
#include <libxml/xmlschemas.h>
/* -------------------------------------------------------------------------- */
#define NO_DESTINATION NULL
/* -------------------------------------------------------------------------- */

View File

@ -32,40 +32,40 @@
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
// Scheduler init function // // Scheduler init function //
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
void sched_init(scheduler_t *scheduler); //void sched_init(scheduler_t *scheduler);
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
// Scheduler content destructor function // // Scheduler content destructor function //
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
static inline void sched_clean (scheduler_t *scheduler) // static inline void sched_clean (scheduler_t *scheduler)
{ // {
assert(scheduler); // assert(scheduler);
if (scheduler->globalDrawingSpace) { // if (scheduler->globalDrawingSpace) {
if (scheduler->globalDrawingSpace->space) { // if (scheduler->globalDrawingSpace->space) {
free(scheduler->globalDrawingSpace->space); // free(scheduler->globalDrawingSpace->space);
scheduler->globalDrawingSpace->space = NULL; // scheduler->globalDrawingSpace->space = NULL;
} // }
free(scheduler->globalDrawingSpace); // free(scheduler->globalDrawingSpace);
scheduler->globalDrawingSpace = NULL; // scheduler->globalDrawingSpace = NULL;
} // }
if (scheduler->arrowArray) { // if (scheduler->arrowArray) {
if (scheduler->arrowArray->array) { // if (scheduler->arrowArray->array) {
free(scheduler->arrowArray->array); // free(scheduler->arrowArray->array);
scheduler->arrowArray->array = NULL; // scheduler->arrowArray->array = NULL;
} // }
free(scheduler->arrowArray); // free(scheduler->arrowArray);
scheduler->arrowArray = NULL; // scheduler->arrowArray = NULL;
} // }
} // }
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
// Scheduler destructor function // // Scheduler destructor function //
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
static inline void sched_shutdown (scheduler_t *scheduler) // static inline void sched_shutdown (scheduler_t *scheduler)
{ // {
assert(scheduler); // assert(scheduler);
free(scheduler); // free(scheduler);
scheduler = NULL; // scheduler = NULL;
} // }

View File

@ -37,4 +37,4 @@
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
// Server init function // // Server init function //
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
void server_init (server_t *server); //void server_init (server_t *server);

View File

@ -30,12 +30,12 @@
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
// Supervisor init function // // Supervisor init function //
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
void superv_init (supervisor_t *supervisor); //void superv_init (supervisor_t *supervisor);
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
// Supervisor destructor function // // Supervisor destructor function //
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
static inline void superv_destroy (supervisor_t *supervisor) // static inline void superv_destroy (supervisor_t *supervisor)
{ // {
; // ;
} // }

View File

@ -30,18 +30,18 @@
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
// Worker init function // // Worker init function //
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
void worker_init(worker_t *worker); //void worker_init(worker_t *worker);
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
// Worker destructor function // // Worker destructor function //
// -------------------------------------------------------------------------- // // -------------------------------------------------------------------------- //
static inline void worker_destroy(worker_t *worker) // static inline void worker_destroy(worker_t *worker)
{ // {
worker->pleaseStop = false; // worker->pleaseStop = false;
worker->terminated = false; // worker->terminated = false;
worker->returnValue = false; // worker->returnValue = false;
worker->id = 0; // worker->id = 0;
free(worker->localWorkAreaCenter); // free(worker->localWorkAreaCenter);
worker->localWorkAreaCenter = NULL; // worker->localWorkAreaCenter = NULL;
} // }

View File

@ -26,15 +26,15 @@
/* -------------------------------------------------------------------------- */ /* -------------------------------------------------------------------------- */
static server_t *server; /* static server_t *server; */
/* static void sig_term_handler(int signum) */ /* static void sig_term_handler(int signum) */
/* { */ /* { */
/* server->pleaseStop = true; */ /* server->pleaseStop = true; */
/* printLog("Server stopping\n"); */ /* printlog("Server stopping\n"); */
/* //XXX ModelShutdown(); */ /* //XXX ModelShutdown(); */
/* printLog("All model shutted down\n"); */ /* printlog("All model shutted down\n"); */
/* } */ /* } */
int main(int argc, char **argv) int main(int argc, char **argv)
@ -42,27 +42,27 @@ int main(int argc, char **argv)
int options; int options;
time_t t; time_t t;
int returnValue = 0; int returnValue = 0;
parameters_t parameters; struct parameters_t parameters = {0};
while ((options = getopt(argc, argv, ":C:M:U:")) != -1) { while ((options = getopt(argc, argv, ":C:M:U:")) != -1) {
switch (options) { switch (options) {
case 'C': case 'C':
printLog("Config : %s\n", optarg); printlog("Config : %s\n", optarg);
parameters.configDir = calloc(1, strlen(optarg) + 1); parameters.configDir = calloc(1, strlen(optarg) + 1);
strcpy(parameters.configDir, optarg); strcpy(parameters.configDir, optarg);
break; break;
case 'M': case 'M':
printLog("Models : %s\n", optarg); printlog("Models : %s\n", optarg);
parameters.modelDir = calloc(1, strlen(optarg) + 1); parameters.modelDir = calloc(1, strlen(optarg) + 1);
strcpy(parameters.modelDir, optarg); strcpy(parameters.modelDir, optarg);
break; break;
case 'U': case 'U':
printLog("Users : %s\n", optarg); printlog("Users : %s\n", optarg);
parameters.userDir = calloc(1, strlen(optarg) + 1); parameters.userDir = calloc(1, strlen(optarg) + 1);
strcpy(parameters.userDir, optarg); strcpy(parameters.userDir, optarg);
break; break;
case ':': case ':':
printErr("Option missing argument : %c\n", optopt); printerr("Option missing argument : %c\n", optopt);
if (parameters.configDir) if (parameters.configDir)
free(parameters.configDir); free(parameters.configDir);
@ -75,7 +75,7 @@ int main(int argc, char **argv)
return ENOSYS; return ENOSYS;
break; break;
case '?': case '?':
printErr("Unknown option : %c\n", optopt); printerr("Unknown option : %c\n", optopt);
if (parameters.configDir) if (parameters.configDir)
free(parameters.configDir); free(parameters.configDir);
@ -91,7 +91,7 @@ int main(int argc, char **argv)
} }
if (!parameters.configDir | !parameters.modelDir | !parameters.userDir) { if (!parameters.configDir | !parameters.modelDir | !parameters.userDir) {
printErr("Missing arguments\n"); printerr("Missing arguments\n");
if (parameters.configDir) if (parameters.configDir)
free(parameters.configDir); free(parameters.configDir);
@ -106,15 +106,15 @@ int main(int argc, char **argv)
} }
// Go! // Go!
printLog("Starting gem-graph-server...\n"); printlog("Starting gem-graph-server...\n");
/* // Register new interrupt handler */ /* // Register new interrupt handler */
/* signal(SIGINT, sig_term_handler); */ /* signal(SIGINT, sig_term_handler); */
/* signal(SIGTERM, sig_term_handler); */ /* signal(SIGTERM, sig_term_handler); */
/* // Initializing random generator */ // Initializing random generator
/* t = time(&t); */ t = time(&t);
/* srand((unsigned) t); */ srand((unsigned)t);
/* server = calloc(1, sizeof(*server)); */ /* server = calloc(1, sizeof(*server)); */

View File

@ -21,7 +21,6 @@
//=-------------------------------------------------------------------------=// //=-------------------------------------------------------------------------=//
#include "../include/model.h" #include "../include/model.h"
#include "../include/parsing.h"
#include "../include/arrows.h" #include "../include/arrows.h"
#include "../include/scheduler.h" #include "../include/scheduler.h"
@ -57,13 +56,13 @@ bool model_init(const char *content, size_t length, const char *basename)
node = xmlDocGetRootElement(model); node = xmlDocGetRootElement(model);
if (node == NULL) { if (node == NULL) {
g_printerr("Empty XML model !\n"); fprintf(stderr, "Empty XML model !\n");
xmlFreeDoc(model); xmlFreeDoc(model);
return false; return false;
} }
if (xmlStrcmp(node->name, (xmlChar *) "gem-graph-model")) { if (xmlStrcmp(node->name, (xmlChar *) "gem-graph-model")) {
g_printerr("document of the wrong type, root node != gem-graph-model\n"); fprintf(stderr, "document of the wrong type, root node != gem-graph-model\n");
xmlFreeDoc(model); xmlFreeDoc(model);
return false; return false;
} }
@ -71,7 +70,7 @@ bool model_init(const char *content, size_t length, const char *basename)
model_hashtable = xmlHashCreate(0); model_hashtable = xmlHashCreate(0);
if (model_hashtable == NULL) { if (model_hashtable == NULL) {
g_printerr("Can't create model hash table !\n"); fprintf(stderr, "Can't create model hash table !\n");
xmlFreeDoc(model); xmlFreeDoc(model);
return false; return false;
} }
@ -117,9 +116,6 @@ static inline xmlChar* getFirstTag(xmlChar *path)
path = (xmlChar *)xmlStrchr(path, '/'); path = (xmlChar *)xmlStrchr(path, '/');
path = xmlStrsub (path, 1, xmlStrlen(path)); path = xmlStrsub (path, 1, xmlStrlen(path));
//printf("%s = %s + / + %s\n", preop,\
xmlStrsub (preop, 0, xmlStrlen(preop) - xmlStrlen(path) - 1), path);
return xmlStrsub (preop, 0, xmlStrlen(preop) - xmlStrlen(path) - 1); return xmlStrsub (preop, 0, xmlStrlen(preop) - xmlStrlen(path) - 1);
} }

View File

@ -25,223 +25,223 @@
/* -------------------------------------------------------------------------- */ /* -------------------------------------------------------------------------- */
static void *server_main(void *server); /* static void *server_main(void *server); */
/* -------------------------------------------------------------------------- */ /* -------------------------------------------------------------------------- */
#define SEND_BUFFER_SIZE 80 * 24 /* #define SEND_BUFFER_SIZE 80 * 24 */
#define RECEIVE_BUFFER_SIZE 80 /* #define RECEIVE_BUFFER_SIZE 80 */
void *server_communication_instance(void *serverCom) /* void *server_communication_instance(void *serverCom) */
{ /* { */
servercom_t *args; /* servercom_t *args; */
char **argv = NULL; /* char **argv = NULL; */
char receiveBuff[RECEIVE_BUFFER_SIZE]; /* char receiveBuff[RECEIVE_BUFFER_SIZE]; */
char sendBuff[SEND_BUFFER_SIZE]; /* char sendBuff[SEND_BUFFER_SIZE]; */
int tokenIndex, bytesReceived, clientPort; /* int tokenIndex, bytesReceived, clientPort; */
char clientIP[16]; /* char clientIP[16]; */
args = (servercom_t*) serverCom; /* args = (servercom_t*) serverCom; */
// Get ip address from client /* // Get ip address from client */
inet_ntop(AF_INET, /* inet_ntop(AF_INET, */
&args->clientAddr.sin_addr, /* &args->clientAddr.sin_addr, */
clientIP, /* clientIP, */
args->sockLen); /* args->sockLen); */
// Get port number from client /* // Get port number from client */
clientPort = ntohs(args->clientAddr.sin_port); /* clientPort = ntohs(args->clientAddr.sin_port); */
//Accept and incoming connection /* //Accept and incoming connection */
while(!args->pleaseStop) { /* while(!args->pleaseStop) { */
// Zeroing buffer /* // Zeroing buffer */
bzero(receiveBuff, RECEIVE_BUFFER_SIZE); /* bzero(receiveBuff, RECEIVE_BUFFER_SIZE); */
//printLog("Waiting for commands...\n"); /* //printLog("Waiting for commands...\n"); */
// Read the message from client and copy it in buffer /* // Read the message from client and copy it in buffer */
bytesReceived = recv(args->sockfd, receiveBuff, RECEIVE_BUFFER_SIZE, 0); /* bytesReceived = recv(args->sockfd, receiveBuff, RECEIVE_BUFFER_SIZE, 0); */
if (bytesReceived == -1) { /* if (bytesReceived == -1) { */
printErr("Could not receive data! (%s)\n", strerror(errno)); /* printErr("Could not receive data! (%s)\n", strerror(errno)); */
break; /* break; */
}; /* }; */
// Ignore null-sized request /* // Ignore null-sized request */
if (bytesReceived == 0) /* if (bytesReceived == 0) */
break; /* break; */
// Print buffer which contains the client request /* // Print buffer which contains the client request */
printLog("Client %s:%d request : '%s'\n", /* printLog("Client %s:%d request : '%s'\n", */
clientIP, /* clientIP, */
clientPort, /* clientPort, */
receiveBuff); /* receiveBuff); */
if (receiveBuff[0] == '\0') //XXX /* if (receiveBuff[0] == '\0') //XXX */
break; /* break; */
// get args in an array /* // get args in an array */
tokenIndex = 0; /* tokenIndex = 0; */
argv = (char**) realloc(argv, 1 * sizeof(char*)); /* argv = (char**) realloc(argv, 1 * sizeof(char*)); */
argv[0] = strtok(receiveBuff, " "); /* argv[0] = strtok(receiveBuff, " "); */
while (argv[tokenIndex]) { /* while (argv[tokenIndex]) { */
tokenIndex++; /* tokenIndex++; */
argv = (char**) realloc(argv, (tokenIndex+1) * sizeof(char*)); /* argv = (char**) realloc(argv, (tokenIndex+1) * sizeof(char*)); */
argv[tokenIndex] = strtok(NULL, " "); /* argv[tokenIndex] = strtok(NULL, " "); */
} /* } */
// Zeroing buffer /* // Zeroing buffer */
bzero(sendBuff, RECEIVE_BUFFER_SIZE); /* bzero(sendBuff, RECEIVE_BUFFER_SIZE); */
// Execute command by first arg in cmdList /* // Execute command by first arg in cmdList */
for (int i = 0; i < LEN(cmdList); i++) { /* for (int i = 0; i < LEN(cmdList); i++) { */
if (strcmp(cmdList[i].name, argv[0]) == 0) { /* if (strcmp(cmdList[i].name, argv[0]) == 0) { */
cmdList[i].execute(sendBuff, argv, args->associatedServer); /* cmdList[i].execute(sendBuff, argv, args->associatedServer); */
} /* } */
} /* } */
// and send that buffer to client /* // and send that buffer to client */
send(args->sockfd, sendBuff, SEND_BUFFER_SIZE, 0); /* send(args->sockfd, sendBuff, SEND_BUFFER_SIZE, 0); */
} /* } */
close(args->sockfd); /* close(args->sockfd); */
if (argv) { /* if (argv) { */
free(argv); /* free(argv); */
argv = NULL; /* argv = NULL; */
} /* } */
printLog("Disconnected from %s:%d\n", clientIP, clientPort); /* printLog("Disconnected from %s:%d\n", clientIP, clientPort); */
return NULL; /* return NULL; */
} /* } */
// -------------------------------------------------------------------------- // /* // -------------------------------------------------------------------------- // */
// Server main function // /* // Server main function // */
// -------------------------------------------------------------------------- // /* // -------------------------------------------------------------------------- // */
#define PORT 9000 /* #define PORT 9000 */
#define MAX_CONNECTION 100 /* #define MAX_CONNECTION 100 */
static void *server_main(void *server) /* static void *server_main(void *server) */
{ /* { */
Server_t *args; /* Server_t *args; */
ServerCommunication_t serverSlots[MAX_CONNECTION] = {0}; /* ServerCommunication_t serverSlots[MAX_CONNECTION] = {0}; */
int connfd, flags, threadStatus, serverSlotIndex = 0; /* int connfd, flags, threadStatus, serverSlotIndex = 0; */
uint socklen; /* uint socklen; */
struct sockaddr_in servaddr; /* struct sockaddr_in servaddr; */
char clientIP[16]; /* char clientIP[16]; */
// Get args /* // Get args */
args = (Server_t*) server; /* args = (Server_t*) server; */
args->returnValue = 0; /* args->returnValue = 0; */
printLog("Server #%lu online\n", args->id); /* printLog("Server #%lu online\n", args->id); */
// Create socket /* // Create socket */
args->sockfd = socket(AF_INET, SOCK_STREAM, 0); /* args->sockfd = socket(AF_INET, SOCK_STREAM, 0); */
if (args->sockfd == -1) { /* if (args->sockfd == -1) { */
printErr("Socket creation failed! (%s)\n", strerror(errno)); /* printErr("Socket creation failed! (%s)\n", strerror(errno)); */
args->returnValue = 1; /* args->returnValue = 1; */
goto serverExiting; /* goto serverExiting; */
} /* } */
// Get socket flags /* // Get socket flags */
flags = fcntl(args->sockfd, F_GETFL); /* flags = fcntl(args->sockfd, F_GETFL); */
if (flags == -1) { /* if (flags == -1) { */
printErr("Socket parameters getting failed! (%s)\n", strerror(errno)); /* printErr("Socket parameters getting failed! (%s)\n", strerror(errno)); */
args->returnValue = 1; /* args->returnValue = 1; */
goto serverExiting; /* goto serverExiting; */
} /* } */
// Change socket flags to non-blocking /* // Change socket flags to non-blocking */
if (fcntl(args->sockfd, F_SETFL, flags | O_NONBLOCK) < 0) { /* if (fcntl(args->sockfd, F_SETFL, flags | O_NONBLOCK) < 0) { */
printErr("Socket non-blocking setting failed! (%s)\n", strerror(errno)); /* printErr("Socket non-blocking setting failed! (%s)\n", strerror(errno)); */
args->returnValue = 1; /* args->returnValue = 1; */
goto serverExiting; /* goto serverExiting; */
} /* } */
// Prepare binding structure /* // Prepare binding structure */
bzero(&servaddr, sizeof(servaddr)); /* bzero(&servaddr, sizeof(servaddr)); */
// Assign IP and PORT /* // Assign IP and PORT */
servaddr.sin_family = AF_INET; /* servaddr.sin_family = AF_INET; */
servaddr.sin_addr.s_addr = htonl(INADDR_ANY); /* servaddr.sin_addr.s_addr = htonl(INADDR_ANY); */
servaddr.sin_port = htons(PORT); /* servaddr.sin_port = htons(PORT); */
// Binding newly created socket /* // Binding newly created socket */
if ((bind(args->sockfd, (struct sockaddr*)&servaddr, /* if ((bind(args->sockfd, (struct sockaddr*)&servaddr, */
sizeof(servaddr))) == -1) { /* sizeof(servaddr))) == -1) { */
printErr("Socket bind failed! (%s)\n", strerror(errno)); /* printErr("Socket bind failed! (%s)\n", strerror(errno)); */
args->returnValue = 1; /* args->returnValue = 1; */
goto serverExiting; /* goto serverExiting; */
} /* } */
// Now server is ready to listen and verification /* // Now server is ready to listen and verification */
if (listen(args->sockfd, MAX_CONNECTION) == -1) { /* if (listen(args->sockfd, MAX_CONNECTION) == -1) { */
printErr("Socket listening failed! (%s)\n", strerror(errno)); /* printErr("Socket listening failed! (%s)\n", strerror(errno)); */
args->returnValue = 1; /* args->returnValue = 1; */
goto serverExiting; /* goto serverExiting; */
} /* } */
socklen = sizeof(struct sockaddr_in); /* socklen = sizeof(struct sockaddr_in); */
// Get server socket address structure /* // Get server socket address structure */
if (getsockname(args->sockfd, (struct sockaddr *)&servaddr, &socklen) /* if (getsockname(args->sockfd, (struct sockaddr *)&servaddr, &socklen) */
== -1) { /* == -1) { */
printErr("Could not get socket structure! (%s)\n", strerror(errno)); /* printErr("Could not get socket structure! (%s)\n", strerror(errno)); */
args->returnValue = 1; /* args->returnValue = 1; */
goto serverExiting; /* goto serverExiting; */
} /* } */
printLog("Server listening...\n"); /* printLog("Server listening...\n"); */
while (!args->pleaseStop) { /* while (!args->pleaseStop) { */
// Accept the data packet from client /* // Accept the data packet from client */
connfd = accept(args->sockfd, /* connfd = accept(args->sockfd, */
(struct sockaddr*) &serverSlots[serverSlotIndex].clientAddr, /* (struct sockaddr*) &serverSlots[serverSlotIndex].clientAddr, */
&socklen); /* &socklen); */
if (connfd < 0) { /* if (connfd < 0) { */
// If error is not due to lack of clients connecting, this is error /* // If error is not due to lack of clients connecting, this is error */
if (errno != EWOULDBLOCK && errno != EAGAIN) { /* if (errno != EWOULDBLOCK && errno != EAGAIN) { */
printErr("Server acccept failed! (%s)\n", strerror(errno)); /* printErr("Server acccept failed! (%s)\n", strerror(errno)); */
goto serverExiting; /* goto serverExiting; */
} /* } */
sleep(1); /* sleep(1); */
} else { /* } else { */
// Client connected /* // Client connected */
// get IP addr from client /* // get IP addr from client */
inet_ntop(AF_INET, /* inet_ntop(AF_INET, */
&(serverSlots[serverSlotIndex].clientAddr.sin_addr), /* &(serverSlots[serverSlotIndex].clientAddr.sin_addr), */
clientIP, socklen); /* clientIP, socklen); */
printLog("Client accepted from %s:%d\n", /* printLog("Client accepted from %s:%d\n", */
clientIP, /* clientIP, */
ntohs(serverSlots[serverSlotIndex].clientAddr.sin_port)); // TODO envisager déplacement dans thread /* ntohs(serverSlots[serverSlotIndex].clientAddr.sin_port)); // TODO envisager déplacement dans thread */
// Populate communicator slot /* // Populate communicator slot */
serverSlots[serverSlotIndex].sockLen = socklen; // XXX /* serverSlots[serverSlotIndex].sockLen = socklen; // XXX */
serverSlots[serverSlotIndex].sockfd = connfd; /* serverSlots[serverSlotIndex].sockfd = connfd; */
serverSlots[serverSlotIndex].associatedServer = args; /* serverSlots[serverSlotIndex].associatedServer = args; */
// Create thread /* // Create thread */
threadStatus = pthread_create(&serverSlots[serverSlotIndex].id, /* threadStatus = pthread_create(&serverSlots[serverSlotIndex].id, */
NULL, /* NULL, */
server_communication_instance, /* server_communication_instance, */
(void*)&serverSlots[serverSlotIndex]); /* (void*)&serverSlots[serverSlotIndex]); */
if(threadStatus != 0) { /* if(threadStatus != 0) { */
printErr("Error from pthread: %d (%s)\n", /* printErr("Error from pthread: %d (%s)\n", */
threadStatus, strerror(errno)); /* threadStatus, strerror(errno)); */
args->returnValue = 1; /* args->returnValue = 1; */
goto serverExiting; /* goto serverExiting; */
} /* } */
serverSlotIndex++; /* serverSlotIndex++; */
//printLog("Accepted connection. Server will now listen...\n"); /* //printLog("Accepted connection. Server will now listen...\n"); */
} /* } */
} /* } */
serverExiting: /* serverExiting: */
for (int i; i < serverSlotIndex; i++) { /* for (int i; i < serverSlotIndex; i++) { */
serverSlots[i].pleaseStop = true; /* serverSlots[i].pleaseStop = true; */
usleep(10000); /* usleep(10000); */
pthread_cancel(serverSlots[i].id); /* pthread_cancel(serverSlots[i].id); */
pthread_join(serverSlots[i].id, NULL); /* pthread_join(serverSlots[i].id, NULL); */
} /* } */
close(args->sockfd); /* close(args->sockfd); */
printLog("Server #%lu offline\n", args->id); /* printLog("Server #%lu offline\n", args->id); */
return NULL; /* return NULL; */
} /* } */