Triton-commits
Threads by month
- ----- 2026 -----
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2025 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2024 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2023 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2022 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2021 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2020 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2019 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2018 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2017 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2016 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2015 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2014 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2013 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2012 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2011 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2010 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
- February
- January
- ----- 2009 -----
- December
- November
- October
- September
- August
- July
- June
- May
- April
- March
December 2009
- 1 participants
- 42 discussions
[Gs-commits] Grayskull Repository branch, master, updated. git-migration-317-g4236223
by noreply@mcs.anl.gov 21 Dec '09
by noreply@mcs.anl.gov 21 Dec '09
21 Dec '09
A ref change was pushed to the repository containing
the project "Grayskull Repository".
The branch, master has been updated
via 42362233e2e4b5394fa45232d6293dd94bbc82b7 (commit)
from 6c5845c03ea5522270cbd1851f3fbbb6fe5c6f7c (commit)
Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.
- Log -----------------------------------------------------------------
commit 42362233e2e4b5394fa45232d6293dd94bbc82b7
Author: Justin Wozniak <wozniak(a)mcs.anl.gov>
Date: Mon Dec 21 15:43:47 2009 -0600
Draft of component diagram from 12/21/2009.
-----------------------------------------------------------------------
Summary of changes:
wiki/proto-architecture.dot | 67 +++++++++++++++++++++++++++++++++++++++++++
1 files changed, 67 insertions(+), 0 deletions(-)
create mode 100644 wiki/proto-architecture.dot
Diff of changes:
diff --git a/wiki/proto-architecture.dot b/wiki/proto-architecture.dot
new file mode 100644
index 0000000..5c574c4
--- /dev/null
+++ b/wiki/proto-architecture.dot
@@ -0,0 +1,67 @@
+digraph prototype {
+
+ overlap = false;
+ splines = true;
+
+ fs [label="FS"];
+ kv [label="KV"];
+ oslc [label="OSL Client"];
+
+ osl1 [label="OSL"];
+ osl2 [label="OSL",color=transparent,fontcolor=transparent];
+ placement [label="Placement"];
+ rebuild [label="Rebuild"];
+ gossip [label="Gossip"];
+ cosd1 [label="COSD"];
+ cosd2 [label="COSD"];
+ dtc1 [label="DTC"];
+ dtc2 [label="DTC"];
+
+ dummy1 [label="dummy",color=transparent,fontcolor=transparent];
+
+ fs -> oslc;
+ kv -> oslc;
+
+ oslc -> osl1;
+
+ subgraph cluster_node_0 {
+
+ label = "node 0";
+ color = black;
+
+ rosd1 [label="ROSD"];
+
+ osl1 -> rosd1;
+ gossip -> rosd1;
+ rosd1 -> gossip;
+
+ rosd1 -> dtc1;
+ rosd1 -> cosd1;
+
+ dtc1 -> cosd1 [color=transparent];
+
+ placement -> rosd1;
+
+ { rank = same; gossip; placement; }
+ gossip -> placement;
+
+ subgraph { rankdir = RL; gossip -> rebuild; }
+ }
+
+ dtc2 -> dtc1;
+ dtc1 -> dtc2;
+
+ subgraph cluster_node_1 {
+
+ label = "node 1";
+ color = black;
+
+ rosd2 [label="ROSD"];
+
+ rosd2 -> dtc2 [color=transparent];
+ dtc2 -> cosd2;
+ }
+
+ { rank = same; fs; kv; dummy1; }
+ { rank = same; dtc1; dtc2; }
+}
hooks/post-receive
--
Grayskull Repository
1
0
[Gs-commits] Grayskull Repository branch, master, updated. git-migration-316-g6c5845c
by noreply@mcs.anl.gov 17 Dec '09
by noreply@mcs.anl.gov 17 Dec '09
17 Dec '09
A ref change was pushed to the repository containing
the project "Grayskull Repository".
The branch, master has been updated
via 6c5845c03ea5522270cbd1851f3fbbb6fe5c6f7c (commit)
via 874d2376cfaaf9d11eb37f75d305ff63d652e231 (commit)
from 7702e040e45ee363873167e70c91419efd5493e7 (commit)
Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.
- Log -----------------------------------------------------------------
commit 6c5845c03ea5522270cbd1851f3fbbb6fe5c6f7c
Author: Phil Carns <carns(a)mcs.anl.gov>
Date: Thu Dec 17 17:08:46 2009 -0500
add cflags for largefile support
commit 874d2376cfaaf9d11eb37f75d305ff63d652e231
Author: Phil Carns <carns(a)mcs.anl.gov>
Date: Thu Dec 17 16:37:05 2009 -0500
move pbranch variables to pwait with pprivate
-----------------------------------------------------------------------
Summary of changes:
code/src/gsl/Makefile.in | 1 +
.../cosd-prototype/test/cosd-bench-concurrent.gs | 21 ++++++++++---------
2 files changed, 12 insertions(+), 10 deletions(-)
Diff of changes:
diff --git a/code/src/gsl/Makefile.in b/code/src/gsl/Makefile.in
index 24169b7..a94c1a7 100644
--- a/code/src/gsl/Makefile.in
+++ b/code/src/gsl/Makefile.in
@@ -58,6 +58,7 @@ BUILD_LDFLAGS = @BUILD_LDFLAGS@
STRICT_CFLAGS = @STRICT_CFLAGS@
CFLAGS= -I$(srcdir)/include -I. -I$(srcdir) @CFLAGS@ @CPPFLAGS@
+CFLAGS += -D_FILE_OFFSET_BITS=64 -D_LARGEFILE64_SOURCE
CWARNS=
ifneq (,$(STRICT_CFLAGS))
CWARNS += -Wcast-align -Wbad-function-cast
diff --git a/code/src/gsl/resources/cosd-prototype/test/cosd-bench-concurrent.gs b/code/src/gsl/resources/cosd-prototype/test/cosd-bench-concurrent.gs
index 0afa938..3e34f9c 100644
--- a/code/src/gsl/resources/cosd-prototype/test/cosd-bench-concurrent.gs
+++ b/code/src/gsl/resources/cosd-prototype/test/cosd-bench-concurrent.gs
@@ -78,20 +78,21 @@ static __blocking int do_cosd_test(void)
pwait
{
- int i;
+ pprivate int i;
+ pprivate struct gs_list_link* tmp_link;
+ pprivate char* buffer = NULL;
+ pprivate uint64_t b_version;
+ pprivate struct bench_op* tmp_op;
+ pprivate int b_ret;
+ /* TODO: make buffer size configurable, and check that
+ * nothing in workload desc is bigger than this
+ */
+ pprivate int64_t buffer_size = 4*1024*1024;
+
for(i=0; i<concurrent; i++)
{
pbranch
{
- struct gs_list_link* tmp_link;
- char* buffer = NULL;
- uint64_t b_version;
- struct bench_op* tmp_op;
- int b_ret;
- /* TODO: make buffer size configurable, and check that
- * nothing in workload desc is bigger than this
- */
- int64_t buffer_size = 4*1024*1024;
buffer = malloc(buffer_size);
assert(buffer);
hooks/post-receive
--
Grayskull Repository
1
0
[Gs-commits] Grayskull Repository branch, master, updated. git-migration-314-g7702e04
by noreply@mcs.anl.gov 17 Dec '09
by noreply@mcs.anl.gov 17 Dec '09
17 Dec '09
A ref change was pushed to the repository containing
the project "Grayskull Repository".
The branch, master has been updated
via 7702e040e45ee363873167e70c91419efd5493e7 (commit)
from bed4c81bd15323110dfee6c35bf7485d11736e99 (commit)
Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.
- Log -----------------------------------------------------------------
commit 7702e040e45ee363873167e70c91419efd5493e7
Author: Phil Carns <carns(a)mcs.anl.gov>
Date: Thu Dec 17 16:17:24 2009 -0500
adding parallelfor3 test case
-----------------------------------------------------------------------
Summary of changes:
code/src/gsl/tests/correctness/module.mk.in | 1 +
.../{parallelfor.gs => parallelfor3.gs} | 11 ++++++++---
2 files changed, 9 insertions(+), 3 deletions(-)
copy code/src/gsl/tests/correctness/{parallelfor.gs => parallelfor3.gs} (80%)
Diff of changes:
diff --git a/code/src/gsl/tests/correctness/module.mk.in b/code/src/gsl/tests/correctness/module.mk.in
index 238abf2..47d9341 100644
--- a/code/src/gsl/tests/correctness/module.mk.in
+++ b/code/src/gsl/tests/correctness/module.mk.in
@@ -13,6 +13,7 @@ GSTESTSRC += $(DIR)/icpfor.gs \
$(DIR)/parallel4.gs \
$(DIR)/parallelfor.gs \
$(DIR)/parallelfor2.gs \
+ $(DIR)/parallelfor3.gs \
$(DIR)/whilebreak.gs \
$(DIR)/whilebreak2.gs \
$(DIR)/whilebreak3.gs \
diff --git a/code/src/gsl/tests/correctness/parallelfor.gs b/code/src/gsl/tests/correctness/parallelfor3.gs
similarity index 80%
copy from code/src/gsl/tests/correctness/parallelfor.gs
copy to code/src/gsl/tests/correctness/parallelfor3.gs
index b2291aa..6eba2e4 100644
--- a/code/src/gsl/tests/correctness/parallelfor.gs
+++ b/code/src/gsl/tests/correctness/parallelfor3.gs
@@ -12,25 +12,30 @@ static __blocking void run_parfor(void)
pwait
{
pprivate int i;
- pprivate int j;
for(i = 0; i < 100; ++i)
{
pbranch
{
- j = i;
+ int foo = i;
+
a[i] = i;
ret[i] = btest1(&a[i]);
assert(ret[i] == 0);
assert(a[i] == (i+1));
- j = i;
+ assert(foo == i);
+
ret[i] = btest2(&a[i]);
assert(ret[i] == 0);
assert(a[i] == (i+3));
+
+ assert(foo == i);
ret[i] = btest3(&a[i]);
assert(ret[i] == 0);
assert(a[i] == (i+6));
+
+ assert(foo == i);
}
}
}
hooks/post-receive
--
Grayskull Repository
1
0
[Gs-commits] Grayskull Repository branch, master, updated. git-migration-313-gbed4c81
by noreply@mcs.anl.gov 17 Dec '09
by noreply@mcs.anl.gov 17 Dec '09
17 Dec '09
A ref change was pushed to the repository containing
the project "Grayskull Repository".
The branch, master has been updated
via bed4c81bd15323110dfee6c35bf7485d11736e99 (commit)
from 065efd31f7ba81701356b4247a781e2d25f18323 (commit)
Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.
- Log -----------------------------------------------------------------
commit bed4c81bd15323110dfee6c35bf7485d11736e99
Author: Phil Carns <carns(a)mcs.anl.gov>
Date: Thu Dec 17 16:12:36 2009 -0500
use pprivate modifier in parallelfor tests
-----------------------------------------------------------------------
Summary of changes:
code/src/gsl/tests/correctness/parallelfor.gs | 3 ++-
code/src/gsl/tests/correctness/parallelfor2.gs | 2 +-
2 files changed, 3 insertions(+), 2 deletions(-)
Diff of changes:
diff --git a/code/src/gsl/tests/correctness/parallelfor.gs b/code/src/gsl/tests/correctness/parallelfor.gs
index 644a511..b2291aa 100644
--- a/code/src/gsl/tests/correctness/parallelfor.gs
+++ b/code/src/gsl/tests/correctness/parallelfor.gs
@@ -11,7 +11,8 @@ static __blocking void run_parfor(void)
pwait
{
- int i, j;
+ pprivate int i;
+ pprivate int j;
for(i = 0; i < 100; ++i)
{
pbranch
diff --git a/code/src/gsl/tests/correctness/parallelfor2.gs b/code/src/gsl/tests/correctness/parallelfor2.gs
index 955e719..b757cfe 100644
--- a/code/src/gsl/tests/correctness/parallelfor2.gs
+++ b/code/src/gsl/tests/correctness/parallelfor2.gs
@@ -15,7 +15,7 @@ static __blocking void run_parfor(
pwait
{
- int i;
+ pprivate int i;
for (i = 0; i < 2; ++i)
{
pbranch
hooks/post-receive
--
Grayskull Repository
1
0
[Gs-commits] Grayskull Repository branch, master, updated. git-migration-312-g065efd3
by noreply@mcs.anl.gov 17 Dec '09
by noreply@mcs.anl.gov 17 Dec '09
17 Dec '09
A ref change was pushed to the repository containing
the project "Grayskull Repository".
The branch, master has been updated
via 065efd31f7ba81701356b4247a781e2d25f18323 (commit)
via 14d3c1cf4ef44e497a73c0923668f63764098248 (commit)
via 97059419ab1477f2a4ad7af200152dc1bacf68a4 (commit)
via a7564eafe2f68a901f0810324de60af62135afc4 (commit)
via 42e2d51f83605823b58c3698459b51f729a2213c (commit)
via 422764ad9859a891dd3f2fe256b03f219d0fad4c (commit)
from c0d9e4b4ab6b283cea7e7f491ea8d0215ff17933 (commit)
Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.
- Log -----------------------------------------------------------------
commit 065efd31f7ba81701356b4247a781e2d25f18323
Author: Phil Carns <carns(a)mcs.anl.gov>
Date: Thu Dec 17 14:59:43 2009 -0500
more assertions for now
commit 14d3c1cf4ef44e497a73c0923668f63764098248
Author: Phil Carns <carns(a)mcs.anl.gov>
Date: Thu Dec 17 14:08:13 2009 -0500
added ability to specify num branches
commit 97059419ab1477f2a4ad7af200152dc1bacf68a4
Author: Phil Carns <carns(a)mcs.anl.gov>
Date: Thu Dec 17 12:53:23 2009 -0500
optional code to make db txns non-durable
commit a7564eafe2f68a901f0810324de60af62135afc4
Author: Phil Carns <carns(a)mcs.anl.gov>
Date: Thu Dec 17 12:39:12 2009 -0500
close cursors before aborting db txns
commit 42e2d51f83605823b58c3698459b51f729a2213c
Author: Phil Carns <carns(a)mcs.anl.gov>
Date: Thu Dec 17 12:35:55 2009 -0500
added counter for db deadlocks & trying out DB_RMW
commit 422764ad9859a891dd3f2fe256b03f219d0fad4c
Author: Phil Carns <carns(a)mcs.anl.gov>
Date: Thu Dec 17 12:08:41 2009 -0500
added timing to cosd-bench-concurrent.gs
-----------------------------------------------------------------------
Summary of changes:
.../gsl/resources/cosd-prototype/cosd-prototype.c | 73 +++++++++++++++++--
.../cosd-prototype/test/cosd-bench-concurrent.gs | 38 +++++++++--
2 files changed, 98 insertions(+), 13 deletions(-)
Diff of changes:
diff --git a/code/src/gsl/resources/cosd-prototype/cosd-prototype.c b/code/src/gsl/resources/cosd-prototype/cosd-prototype.c
index dfda80e..c6ef7a1 100644
--- a/code/src/gsl/resources/cosd-prototype/cosd-prototype.c
+++ b/code/src/gsl/resources/cosd-prototype/cosd-prototype.c
@@ -111,6 +111,8 @@ static int completed_counter = 0;
static gs_mutex_t completed_counter_mutex = GS_MUTEX_INITIALIZER;
static gs_cond_t completed_counter_cond = GS_COND_INITIALIZER;
+static unsigned long deadlock_counter = 0;
+
/* uniquely identifies each active txn (in memory) */
struct txn_accumulator
{
@@ -467,6 +469,17 @@ int gs_cosd_init(enum progress_mode mode, const char* path)
return(-1);
}
+#if 0
+ /* purely for experimental purposes at this point */
+ /* make transactions non-durable */
+ ret = envp->set_flags(envp, DB_TXN_NOSYNC, 1);
+ if(ret != 0)
+ {
+ /* TODO: error handling */
+ return(-1);
+ }
+#endif
+
/* have db do deadlock detection and reject txn with fewest locks */
ret = envp->set_lk_detect(envp, DB_LOCK_MINWRITE);
if(ret != 0)
@@ -639,6 +652,8 @@ int gs_cosd_finalize(void)
gs_hash_finalize(txn_table);
gs_mutex_unlock(&txn_mutex);
+ printf("deadlock_counter: %lu\n", deadlock_counter);
+
return 0;
}
@@ -701,7 +716,7 @@ static int write_op_worker(struct gs_op* op)
if(ret < 0)
{
c_op->error_code = -errno;
- return(1);
+ assert(0);
}
global_fd = ret;
}
@@ -717,7 +732,7 @@ static int write_op_worker(struct gs_op* op)
{
/* TODO: err handling */
c_op->error_code = -errno;
- return(1);
+ assert(0);
}
/* find the next chunk that is contiguous in memory and disk */
@@ -778,7 +793,7 @@ write_op_txn:
{
/* TODO: error handling */
c_op->error_code = -1;
- return(1);
+ assert(0);
}
ret = log_offset_dbp->get(log_offset_dbp, txn, &key, &value, 0);
@@ -786,11 +801,14 @@ write_op_txn:
{
txn->abort(txn);
if(ret == DB_LOCK_DEADLOCK)
+ {
+ deadlock_counter++;
goto write_op_txn;
+ }
/* TODO: error handling */
c_op->error_code = -1;
- return(1);
+ assert(0);
}
ret = txn->commit(txn, 0);
@@ -798,7 +816,10 @@ write_op_txn:
{
txn->abort(txn);
if(ret == DB_LOCK_DEADLOCK)
+ {
+ deadlock_counter++;
goto write_op_txn;
+ }
/* TODO: error handling */
assert(0);
@@ -826,7 +847,7 @@ write_op_txn:
{
/* TODO: err handling */
c_op->error_code = -errno;
- return(1);
+ assert(0);
}
}
memcpy(scratch_buffer, mem_ptr, tmp_update->size);
@@ -840,7 +861,7 @@ write_op_txn:
{
/* TODO: err handling */
c_op->error_code = -errno;
- return(1);
+ assert(0);
}
/* track this update in the txn accumulator */
@@ -1412,7 +1433,10 @@ txn_close_op_retry:
{
txn->abort(txn);
if(ret == DB_LOCK_DEADLOCK)
+ {
+ deadlock_counter++;
goto txn_close_op_retry;
+ }
/* TODO: error handling */
assert(0);
}
@@ -1434,7 +1458,10 @@ txn_close_op_retry:
while(!done)
{
/* get each potentially overlapping on disk region */
- ret = dbc_p->c_get(dbc_p, &key, &value, c_get_flag);
+ /* TODO: remove RMW flag if we change this to not replace all
+ * keys
+ */
+ ret = dbc_p->c_get(dbc_p, &key, &value, (c_get_flag|DB_RMW));
if(ret == DB_NOTFOUND)
{
done = 1;
@@ -1442,9 +1469,13 @@ txn_close_op_retry:
}
if(ret != 0)
{
+ dbc_p->c_close(dbc_p);
txn->abort(txn);
if(ret == DB_LOCK_DEADLOCK)
+ {
+ deadlock_counter++;
goto txn_close_op_retry;
+ }
/* TODO: err handling */
assert(0);
}
@@ -1476,9 +1507,13 @@ txn_close_op_retry:
ret = dbc_p->c_del(dbc_p, 0);
if(ret != 0)
{
+ dbc_p->c_close(dbc_p);
txn->abort(txn);
if(ret == DB_LOCK_DEADLOCK)
+ {
+ deadlock_counter++;
goto txn_close_op_retry;
+ }
/* TODO: err handling */
assert(0);
}
@@ -1489,7 +1524,10 @@ txn_close_op_retry:
{
txn->abort(txn);
if(ret == DB_LOCK_DEADLOCK)
+ {
+ deadlock_counter++;
goto txn_close_op_retry;
+ }
/* TODO: error handling */
assert(0);
}
@@ -1517,7 +1555,10 @@ txn_close_op_retry:
txn->abort(txn);
free(free_ptr);
if(ret == DB_LOCK_DEADLOCK)
+ {
+ deadlock_counter++;
goto txn_close_op_retry;
+ }
/* TODO: err handling */
assert(0);
}
@@ -1528,12 +1569,15 @@ txn_close_op_retry:
COSD_INIT_DBT(key, c_op->u.txn_close.oid);
COSD_INIT_DBT(value, version);
- ret = ver_dbp->get(ver_dbp, txn, &key, &value, 0);
+ ret = ver_dbp->get(ver_dbp, txn, &key, &value, DB_RMW);
if(ret != 0)
{
txn->abort(txn);
if(ret == DB_LOCK_DEADLOCK)
+ {
+ deadlock_counter++;
goto txn_close_op_retry;
+ }
/* TODO: error handling */
assert(0);
@@ -1558,7 +1602,10 @@ txn_close_op_retry:
{
txn->abort(txn);
if(ret == DB_LOCK_DEADLOCK)
+ {
+ deadlock_counter++;
goto txn_close_op_retry;
+ }
/* TODO: error handling */
assert(0);
}
@@ -1573,7 +1620,10 @@ txn_close_op_retry:
{
txn->abort(txn);
if(ret == DB_LOCK_DEADLOCK)
+ {
+ deadlock_counter++;
goto txn_close_op_retry;
+ }
/* TODO: error handling */
assert(0);
}
@@ -1593,6 +1643,7 @@ txn_close_op_retry:
if(ret == DB_LOCK_DEADLOCK)
{
txn->abort(txn);
+ deadlock_counter++;
goto txn_close_op_retry;
}
if(ret != 0 && ret != DB_NOTFOUND)
@@ -1616,7 +1667,10 @@ txn_close_op_retry:
{
txn->abort(txn);
if(ret == DB_LOCK_DEADLOCK)
+ {
+ deadlock_counter++;
goto txn_close_op_retry;
+ }
/* TODO: error handling */
assert(0);
@@ -1628,7 +1682,10 @@ txn_close_op_retry:
{
txn->abort(txn);
if(ret == DB_LOCK_DEADLOCK)
+ {
+ deadlock_counter++;
goto txn_close_op_retry;
+ }
/* TODO: error handling */
assert(0);
diff --git a/code/src/gsl/resources/cosd-prototype/test/cosd-bench-concurrent.gs b/code/src/gsl/resources/cosd-prototype/test/cosd-bench-concurrent.gs
index 3be7aed..0afa938 100644
--- a/code/src/gsl/resources/cosd-prototype/test/cosd-bench-concurrent.gs
+++ b/code/src/gsl/resources/cosd-prototype/test/cosd-bench-concurrent.gs
@@ -1,6 +1,7 @@
#include <stdio.h>
#include <errno.h>
+#include <sys/time.h>
#include "../../../include/gs.h"
#include "../cosd-prototype.gsh"
#include "gs-config.h"
@@ -37,6 +38,17 @@ struct bench_op
GS_LIST_HEAD(op_list);
gs_mutex_t op_list_mutex = GS_MUTEX_INITIALIZER;
+static double Wtime(void)
+{
+ struct timeval t;
+ gettimeofday(&t, NULL);
+ return((double)t.tv_sec + (double)(t.tv_usec) / 1000000);
+}
+static double start_tm;
+static double end_tm;
+static int64_t total_size = 0;
+int concurrent;
+
static __blocking int do_cosd_test(void)
{
int ret;
@@ -62,11 +74,12 @@ static __blocking int do_cosd_test(void)
return(1);
}
+ start_tm = Wtime();
+
pwait
{
int i;
- /* TODO: make "16" tunable */
- for(i=0; i<16; i++)
+ for(i=0; i<concurrent; i++)
{
pbranch
{
@@ -100,6 +113,7 @@ static __blocking int do_cosd_test(void)
assert(0);
}
+ total_size += tmp_op->size;
b_ret = gs_cosd_write(1, b_version, &buffer,
&buffer_size, 1, &tmp_op->offset, &tmp_op->size, 1);
if(b_ret < 0)
@@ -123,6 +137,7 @@ static __blocking int do_cosd_test(void)
}
}
}
+ end_tm = Wtime();
#if 0
ret = gs_cosd_dump();
@@ -153,9 +168,9 @@ int main(int argc, char *argv[])
int ret;
struct bench_op* tmp_op;
- if(argc != 4)
+ if(argc != 5)
{
- fprintf(stderr, "Usage: cosd1 <1|2> <workload description file> <cosd dir>\n");
+ fprintf(stderr, "Usage: cosd1 <1|2> <workload description file> <cosd dir> <concurrent ops>\n");
fprintf(stderr, " # 1 for polling\n");
fprintf(stderr, " # 2 for thread-per-op\n");
return(-1);
@@ -164,12 +179,20 @@ int main(int argc, char *argv[])
sscanf(argv[1], "%d", &mode);
if(mode > 2 || mode < 1)
{
- fprintf(stderr, "Usage: cosd1 <1|2>\n");
+ fprintf(stderr, "Usage: cosd1 <1|2> <workload description file> <cosd dir> <concurrent ops>\n");
fprintf(stderr, " # 1 for polling\n");
fprintf(stderr, " # 2 for thread-per-op\n");
return(-1);
}
+ ret = sscanf(argv[4], "%d", &concurrent);
+ if(ret != 1 || concurrent < 1)
+ {
+ fprintf(stderr, "Usage: cosd1 <1|2> <workload description file> <cosd dir> <concurrent ops>\n");
+ fprintf(stderr, " # 1 for polling\n");
+ fprintf(stderr, " # 2 for thread-per-op\n");
+ }
+
/* parse description of workload */
desc = fopen(argv[2], "r");
if(!desc)
@@ -222,6 +245,11 @@ int main(int argc, char *argv[])
gs_cosd_finalize();
gs_context_destroy(ctx);
+
+ printf("# Moved %lld bytes in %f seconds.\n", lld(total_size),
+ (end_tm-start_tm));
+ printf("%f MB/s\n", (((double)total_size)/(1024.0*1024.0))/(end_tm-start_tm));
+
return 0;
}
hooks/post-receive
--
Grayskull Repository
1
0
[Gs-commits] Grayskull Repository branch, master, updated. git-migration-306-gc0d9e4b
by noreply@mcs.anl.gov 17 Dec '09
by noreply@mcs.anl.gov 17 Dec '09
17 Dec '09
A ref change was pushed to the repository containing
the project "Grayskull Repository".
The branch, master has been updated
via c0d9e4b4ab6b283cea7e7f491ea8d0215ff17933 (commit)
from 80083cfdfe7b0950eec19f57a6ec12d8774c3351 (commit)
Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.
- Log -----------------------------------------------------------------
commit c0d9e4b4ab6b283cea7e7f491ea8d0215ff17933
Author: Samuel Lang <slang(a)bblogin.mcs.anl.gov>
Date: Thu Dec 17 14:06:44 2009 -0600
Revert "some type infrastructure for remote encoding/decoding."
This reverts commit 80083cfdfe7b0950eec19f57a6ec12d8774c3351.
-----------------------------------------------------------------------
Summary of changes:
code/src/gsl/common/gs-buffer.h | 73 -----
code/src/gsl/common/gs-count-list.h | 126 --------
code/src/gsl/common/gs-debug.h | 16 -
code/src/gsl/common/gs-error.h | 86 ------
code/src/gsl/common/gs-list.h | 230 ---------------
code/src/gsl/common/gs-node.h | 15 -
code/src/gsl/common/gs-safe-list.h | 161 ----------
code/src/gsl/common/gs-types.h | 17 -
code/src/gsl/{common => include}/gs-hash.h | 0
code/src/gsl/{common => include}/gs.h | 3 +
code/src/gsl/parser/gs-remote-parser.lhs | 8 +-
code/src/gsl/proto/gs-byteswap.h | 112 -------
code/src/gsl/proto/gs-encoding-pw.h | 442 ----------------------------
code/src/gsl/proto/gs-encoding.h | 7 -
14 files changed, 7 insertions(+), 1289 deletions(-)
delete mode 100644 code/src/gsl/common/gs-buffer.h
delete mode 100644 code/src/gsl/common/gs-count-list.h
delete mode 100644 code/src/gsl/common/gs-debug.h
delete mode 100644 code/src/gsl/common/gs-error.h
delete mode 100644 code/src/gsl/common/gs-list.h
delete mode 100644 code/src/gsl/common/gs-node.h
delete mode 100644 code/src/gsl/common/gs-safe-list.h
delete mode 100644 code/src/gsl/common/gs-types.h
rename code/src/gsl/{common => include}/gs-hash.h (100%)
rename code/src/gsl/{common => include}/gs.h (98%)
delete mode 100644 code/src/gsl/proto/gs-byteswap.h
delete mode 100644 code/src/gsl/proto/gs-encoding-pw.h
delete mode 100644 code/src/gsl/proto/gs-encoding.h
Diff of changes:
diff --git a/code/src/gsl/common/gs-buffer.h b/code/src/gsl/common/gs-buffer.h
deleted file mode 100644
index 5ee944e..0000000
--- a/code/src/gsl/common/gs-buffer.h
+++ /dev/null
@@ -1,73 +0,0 @@
-#ifndef __GS_BUFFER_H__
-#define __GS_BUFFER_H__
-
-#include <stdlib.h>
-#ifdef HAVE_MALLOC_H
-#include <malloc.h>
-#endif
-
-#include "common/gs-types.h"
-
-/* We require a max size for a buffer, to prevent clients from requesting
- * (perhaps due to a bug or bit-flip somewhere) more memory than is available
- * on the machine.
- */
-
-/**
- * The buffer type is used for generic byte streams. A current pointer field
- * is included allowing the buffer to be used by encoding/decoding mechanisms
- * before being transmitted. The buffer type can be encoded itself, allowing
- * it to be used as a generic buffer type.
- */
-typedef struct
-{
- void *buffer;
- uint64_t size;
- void *cptr;
-} gs_buffer_t;
-
-#define GS_BUFFER_STATIC_INITIALIZER() = { NULL, 0, NULL }
-
-#define gs_buffer_cptr(__buf) ((__buf)->cptr)
-
-static inline gs_ret_t gs_buffer_alloc(gs_buffer_t *buffer, int64_t size)
-{
- (*buffer)->buffer = malloc(sizeof(*(*buffer)->buffer) * size);
- if(!(*buffer)->buffer)
- {
- return gs_error_errno(ENOMEM);
- }
- (*buffer)->size = size;
- gs_buffer_ptr_reset(buffer);
- return GS_SUCCESS;
-}
-
-static inline void gs_buffer_free(gs_buffer_t *buffer)
-{
- if(buffer && buffer->buffer) free(buffer->buffer);
- buffer->buffer = NULL;
- buffer->cptr = NULL;
- buffer->size = 0;
-}
-
-static inline void gs_buffer_ptr_reset(gs_buffer_t *buffer)
-{
- buffer->cptr = buffer->buffer;
-}
-
-/* The buffer_check_overflow macro verfies that the current buffer pointer is not
- * at the end of the buffer, and that there's enough space left for __inc bytes.
- */
-#define gs_buffer_check_overflow(__buf, __inc) do { \
- if((__buf)->size < (((__buf)->cptr - (__buf)->buffer) + (__inc))) \
- { \
- return gs_error_errno(EOVERFLOW); \
- } \
-} while(0)
-
-/* Increment the current buffer pointer */
-#define gs_buffer_inc(__buf, __inc) do { \
- (__buf)->cptr+=(__inc); \
-} while(0)
-
-#endif /* __GS_BUFFER_H__ */
diff --git a/code/src/gsl/common/gs-count-list.h b/code/src/gsl/common/gs-count-list.h
deleted file mode 100644
index 1aec02c..0000000
--- a/code/src/gsl/common/gs-count-list.h
+++ /dev/null
@@ -1,126 +0,0 @@
-#ifndef __GS_COUNT_LIST_H__
-#define __GS_COUNT_LIST_H__
-
-#include "common/gs-list.h"
-
-typedef struct
-{
- gs_list_t list;
- uin64_t count;
-} gs_countlist_t;
-
-typedef struct
-{
- gs_countlist_t *inlist;
- struct gs_list_link link;
-} gs_countlist_link_t;
-
-#define GS_COUNT_LIST_NULL { { NULL, NULL }, 0 }
-
-#define GS_COUNT_LIST_STATIC_INITIALIZER(name) { { &(name), &(name) }, 0 }
-
-#define GS_COUNT_LIST_DEFINE(name) \
- gs_countlist_t name = GS_COUNT_LIST_STATIC_INITIALIZER(name)
-
-#define gs_countlist_link_clear(__link) do { \
- (__link)->inlist = NULL; \
- gs_list_link_clear(&((__link)->link)); \
-} while(0)
-
-static inline void gs_countlist_init(gs_countlist_t *clist)
-{
- gs_list_init(&clist->list);
- clist->count = 0;
-}
-
-static inline void gs_countlist_add(
- struct gs_countlist_link_t *new, gs_countlist_t *clist)
-{
- assert(new->inlist == NULL);
- assert(new->link.next == NULL && new->link.prev == NULL);
- gs_list_add(&new->link, clist->list);
- clist->count++;
-}
-
-static inline void gs_countlist_add_tail(
- gs_countlist_link_t *new, gs_countlist_t *clist)
-{
- assert(new->inlist == NULL);
- assert(new->link.next == NULL && new->link.prev == NULL);
- gs_list_add_tail(&new->link, clist->list);
- clist->count++;
-}
-
-static inline void gs_countlist_del(
- gs_countlist_link_t *entry, gs_countlist_t *clist)
-{
- assert(entry->link.next != NULL && entry->link.prev != NULL);
- assert(entry->inlist == clist);
- gs_list_del(&entry->link);
- clist->count--;
- CLEAR_GS_LIST_LINK(entry->link);
-}
-
-static inline int gs_countlist_empty(gs_countlist_t *clist)
-{
- return clist->count == 0;
-}
-
-#define gs_countlist_push(_op, _clist) gs_countlist_add_tail(_op, _clist)
-
-static inline gs_countlist_link_t *gs_countlist_pop(gs_countlist_t *list)
-{
- struct gs_countlist_link *entry;
- if(gs_countlist_empty(list)) return NULL;
- entry = gs_list_get_entry(gs_list_pop(&list->list), gs_countlist_link_t, link);
- countlist->count--;
- CLEAR_GS_LIST_LINK(entry);
- assert(((gs_countlist_t *)entry->inlist) == list);
- entry->inlist = NULL;
- return entry;
-}
-
-#define gs_countlist_peek(_list) \
- gs_list_get_entry(gs_list_peek(&(_list)->list), gs_countlist_link_t, link)
-
-#define gs_countlist_get_entry(ptr, type, member) \
- gs_list_get_entry(ptr, type, member)
-
-#define gs_countlist_link_from_list_link(_ptr) \
- gs_list_get_entry(_ptr, gs_countlist_link_t, link)
-
-/* these are automatically safe for removal during iteration */
-
-#define gs_countlist_exists(clist, llink) gs_list_exists(&(clist->list), llink)
-
-#define gs_countlist_find(clist, compare, ptr) \
- gs_countlist_find(&(clist->list), compare, ptr)
-
-#define gs_countlist_push(__list, __entry) gs_list_push(&(__list)->list, __entry)
-
-#define gs_countlist_pop(__list) gs_list_pop(&(__list)->list)
-
-#define gs_countlist_peek(__list) gs_list_peek(&(__list)->list)
-
-static inline uint64_t gs_countlist_size(gs_countlist_t *list)
-{
- return list->count;
-}
-
-static inline gs_countlist_link_t *gs_countlist_find(
- gs_countlist_t *list,
- int (*compare)(struct gs_countlist_link_t *, void *),
- void *ptr)
-{
- struct gs_countlist_link_t *llink;
- gs_countlist_for_each(llink, list)
- {
- if(compare(llink, list))
- {
- return llink;
- }
- }
- return NULL;
-}
-
-#endif /* __GS_COUNT_LIST_H__ */
diff --git a/code/src/gsl/common/gs-debug.h b/code/src/gsl/common/gs-debug.h
deleted file mode 100644
index d0e9481..0000000
--- a/code/src/gsl/common/gs-debug.h
+++ /dev/null
@@ -1,16 +0,0 @@
-enum gs_debug_mask
-{
- GS_DEBUG_LEVEL0 = 0,
- GS_DEBUG_LEVEL1 = 1,
- GS_DEBUG_LEVEL2 = 2
-};
-
-/**
- * Debugging is used by developers during development when writing code
- * and debugging their code in distributed environments. It is not
- * meant for providing information to end-users.
- */
-uint32_t gs_debug(enum gs_debug_mask mask,
- char *message);
-
-
diff --git a/code/src/gsl/common/gs-error.h b/code/src/gsl/common/gs-error.h
deleted file mode 100644
index afe45d0..0000000
--- a/code/src/gsl/common/gs-error.h
+++ /dev/null
@@ -1,86 +0,0 @@
-#ifndef __GS_ERROR_H__
-#define __GS_ERROR_H__
-
-#define GS_ERR_MASK (1 << 7)
-#define GS_ECANCELLED (GS_ERR_MASK | 1)
-
-/**
- * This struct is used internally by the gs_error_t type, defined below.
- *
- * The error message adds information useful to the consumer of the error
- * (the user or administrator). Error messages are tagged with the location
- * (the node) where the error message was added to the error structure.
- * Error messages are optional! In order to maintain a lightweight error
- * interface, error messages should only be added to errors where the error
- * is clearly an unrecoverable error. The error interfaces provide constructs
- * both for errors with and without messages.
- */
-struct gs_error_message
-{
- gs_node_t location;
- gs_string_t *message;
- gs_countlist_link_t link; /* we use countlist to allow for encoding */
-};
-
-/**
- * The error type allows errors to be wrapped in an error type, useful
- * for managing error codes, logging errors in a consistent format, and
- * later finger-pointing of errors. This structure and the
- * companion error interfaces should be used throughout the entire framework.
- * Errors in responses should
- * be in the gs_error_t format, and errors from resources and other components
- * should use this type as well.
- * The error structure consists of a single error code for the
- * error, the source node where the error is generated, and optional error
- * messages.
- */
-typedef struct
-{
- gs_node_t node;
- int32_t error_code;
- gs_countlist_t messages;
-} gs_error_t;
-
-typedef gs_error_t gs_ret_t;
-
-#define GS_SUCCESS { GS_NODE_NULL, GS_ERROR_NONE, GS_COUNT_LIST_NULL }
-
-/**
- * Wrap an error code as a gs_error_t error. This will clear the
- * other fields in the error, and set the node to the current
- * node.
- *
- * This is a lightweight interface to
- * construct a gs_error_t type, useful for recoverable errors.
- */
-void gs_error_wrap(
- int32_t error_code,
- gs_error_t *error);
-
-/**
- * Create a gs_error_t type from an error code, and include a message
- * about the error. The message gets copied to the resulting error
- * structure, so it can be freed after the error returns. The returned
- * error structure is a heap variable, a companion call to gs_error_free
- * is required.
- */
-gs_error_t *gs_error_create(
- int32_t error_code,
- char *message /** An optional message to add to the error */);
-
-/**
- * Add a message to the set of error messages within an error structure. This
- * function allows for finger-pointing and path-following of
- * errors that pass through multiple nodes. The current node is added
- * with the message to the stack of messages.
- */
-void gs_error_add_message(
- gs_error_t *error,
- char *message);
-
-/**
- * Free an error that was created with gs_error_create.
- */
-void gs_error_destroy(gs_error_t *error);
-
-#endif /* __GS_ERROR_H__ */
diff --git a/code/src/gsl/common/gs-list.h b/code/src/gsl/common/gs-list.h
deleted file mode 100644
index d2dc62f..0000000
--- a/code/src/gsl/common/gs-list.h
+++ /dev/null
@@ -1,230 +0,0 @@
-#ifndef __GS_LIST_H__
-#define __GS_LIST_H__
-
-#ifdef __STRICT_ANSI__
-#define inline __inline__
-#endif
-
-#include <stdlib.h>
-#include <assert.h>
-
-typedef struct gs_list_link gs_list_link_t;
-struct gs_list_link {
- struct gs_list_link *next, *prev;
-};
-
-typedef gs_list_link_t gs_list_t;
-
-#define GS_LIST_STATIC_INITIALIZER(name) { &(name), &(name) }
-
-#define GS_LIST_DEFINE(name) \
- gs_list_t name = GS_LIST_STATIC_INITIALIZER(name)
-
-static inline void gs_list_init(gs_list_t *list)
-{
- list->next = (struct gs_list_link *)list;
- list->prev = (struct gs_list_link *)list;
-}
-
-static inline void gs_list_link_clear(gs_list_link_t *llink)
-{
- ((struct gs_list_link *)llink)->next = NULL;
- ((struct gs_list_link *)llink)->prev = NULL;
-}
-
-/*
- * Insert a new entry between two known consecutive entries.
- *
- * This is only for internal gs_list manipulation where we know
- * the prev/next entries already!
- */
-static inline void __gs_list_add(struct gs_list_link * new,
- struct gs_list_link * prev,
- struct gs_list_link * next)
-{
- next->prev = new;
- new->next = next;
- new->prev = prev;
- prev->next = new;
-}
-
-/**
- * gs_list_add - add a new entry
- * @new: new entry to be added
- * @head: gs_list head to add it after
- *
- * Insert a new entry after the specified head.
- * This is good for implementing stacks.
- */
-static inline void gs_list_add(struct gs_list_link *new, gs_list_t *head)
-{
- __gs_list_add(new, head, head->next);
-}
-
-/**
- * gs_list_add_tail - add a new entry
- * @new: new entry to be added
- * @head: gs_list head to add it before
- *
- * Insert a new entry before the specified head.
- * This is useful for implementing queues.
- */
-static inline void gs_list_add_tail(struct gs_list_link *new, gs_list_t *head)
-{
- __gs_list_add(new, head->prev, head);
-}
-
-/*
- * Delete a gs_list entry by making the prev/next entries
- * point to each other.
- *
- * This is only for internal gs_list manipulation where we know
- * the prev/next entries already!
- */
-static inline void __gs_list_del(struct gs_list_link * prev,
- struct gs_list_link * next)
-{
- next->prev = prev;
- prev->next = next;
-}
-
-/**
- * gs_list_del - deletes entry from gs_list.
- * @entry: the element to delete from the gs_list.
- * Note: gs_list_empty on entry does not return true after this, the entry is in an undefined state.
- */
-static inline void gs_list_del(struct gs_list_link *entry)
-{
- assert(entry->prev != NULL && entry->next != NULL);
- __gs_list_del(entry->prev, entry->next);
- entry->prev = NULL; entry->next = NULL;
-}
-
-/**
- * gs_list_del_clear - deletes entry from gs_list and reinitialize it.
- * @entry: the element to delete from the gs_list.
- */
-static inline void gs_list_del_clear(struct gs_list_link *entry)
-{
- __gs_list_del(entry->prev, entry->next);
- gs_list_link_clear(entry);
-}
-
-/**
- * gs_list_empty - tests whether a gs_list is empty
- * @head: the gs_list to test.
- */
-static inline int gs_list_empty(gs_list_t *head)
-{
- return head->next == head;
-}
-
-/**
- * gs_list_splice - join two gs_lists
- * @gs_list: the new gs_list to add.
- * @head: the place to add it in the first gs_list.
- */
-static inline void gs_list_splice(gs_list_t *gs_list, struct gs_list_link *llink)
-{
- struct gs_list_link *first = gs_list->next;
-
- if (first != gs_list) {
- struct gs_list_link *last = gs_list->prev;
- struct gs_list_link *at = llink->next;
-
- first->prev = llink;
- llink->next = first;
-
- last->next = at;
- at->prev = last;
- }
-}
-
-/**
- * gs_list_get_entry - get the struct for this entry
- * @ptr: the &struct gs_list_link pointer.
- * @type: the type of the struct this is embedded in.
- * @member: the name of the gs_list_struct within the struct.
- */
-#define gs_list_get_entry(ptr, type, member) \
- ((ptr != NULL) ? ((type *)((char *)(ptr)-(unsigned long)((&((type *)0)->member)))) : NULL)
-
-/**
- * gs_list_for_each - iterate over a list safe against removal of list entry
- * @pos: the struct gs_list_link * to use as a loop counter.
- */
-#define gs_list_for_each(pos, head) \
- for (struct gs_list_link *scratch = ((struct gs_list_link *)head)->next, \
- pos = ((struct gs_list_link *)head)->next; \
- pos != ((struct gs_list_link *)head); \
- pos = scratch, scratch = pos->next)
-
-/**
- * gs_list_for_each_entry -
- * iterate over list of given type safe against removal of list entry
- * @pos: the type * to use as a loop counter.
- * @head: the head for your list.
- * @member: the name of the list_struct within the struct.
- */
-#define gs_list_for_each_entry(pos, head, member) \
- for (struct gs_list_link *scratch = (head)->next, \
- pos = gs_list_get_entry((head)->next, typeof(*pos), member); \
- pos && (&pos->member != (head)); \
- pos = gs_list_get_entry(scratch, typeof(*pos), member), \
- scratch = pos->member.next)
-
-static inline int gs_list_exists(gs_list_t *list, struct gs_list_link *llink)
-{
- struct gs_list_link *mypos;
- gs_list_for_each(mypos, list)
- {
- if(mypos == llink)
- {
- return 1;
- }
- }
- return 0;
-}
-
-static inline struct gs_list_link * gs_list_find(
- gs_list_t *list,
- int (*compare)(struct gs_list_link *, void *),
- void *ptr)
-{
- struct gs_list_link *pos;
- gs_list_for_each(pos, list)
- {
- if(compare(pos, ptr))
- {
- return pos;
- }
- }
- return NULL;
-}
-
-#define gs_list_push(__list, __entry) gs_list_add_tail((__entry), (__list))
-
-static inline struct gs_list_link * gs_list_pop(gs_list_t *list)
-{
- struct gs_list_link *entry = list->next;
- if(gs_list_empty(list)) return NULL;
- gs_list_del(list->next);
- return entry;
-}
-
-static inline struct gs_list_link *gs_list_peek(gs_list_t *list)
-{
- if(list->next == list) return NULL;
- return list->next;
-}
-
-#endif
-
-/*
- * Local variables:
- * c-indent-level: 4
- * c-basic-offset: 4
- * End:
- *
- * vim: ts=8 sts=4 sw=4 expandtab
- */
diff --git a/code/src/gsl/common/gs-node.h b/code/src/gsl/common/gs-node.h
deleted file mode 100644
index 7d3193d..0000000
--- a/code/src/gsl/common/gs-node.h
+++ /dev/null
@@ -1,15 +0,0 @@
-#ifndef __GS_NODE_H__
-#define __GS_NODE_H__
-
-#include "common/gs-types.h"
-
-/**
- * The gs_node_t is an opaque address for a node in the system.
- */
-typedef uint128_t gs_node_t;
-
-gs_node_t gs_mynode(void);
-
-void gs_set_mynode(gs_node_t node);
-
-#endif /* __GS_NODE_H__ */
diff --git a/code/src/gsl/common/gs-safe-list.h b/code/src/gsl/common/gs-safe-list.h
deleted file mode 100644
index cfc6f1e..0000000
--- a/code/src/gsl/common/gs-safe-list.h
+++ /dev/null
@@ -1,161 +0,0 @@
-#ifndef __GS_SAFE_LIST_H__
-#define __GS_SAFE_LIST_H__
-
-#ifdef __STRICT_ANSI__
-/* strict ANSI C doesn't have 'inline' functions, so we use __inline__ instead */
-#define inline __inline__
-#endif
-
-#include "include/gs-count-list.h"
-
-typedef struct
-{
- gs_countlist_t list;
- gs_mutex_t mutex;
-} gs_safelist_t;
-
-typedef gs_countlist_link_t gs_safelist_link_t;
-
-#define GS_SAFE_LIST_STATIC_INITIALIZER(name) \
- { { { &(name), &(name) }, 0 }, GS_MUTEX_INITIALIZER }
-
-#define GS_SAFE_LIST_DEFINE(name) \
- gs_safelist_t name = GS_SAFE_LIST_STATIC_INITIALIZER(name)
-
-#define gs_safelist_link_clear(__link) do { \
- gs_list_link_clear(&((__link)->link)); \
-} while(0)
-
-static inline void gs_safelist_init(gs_safelist_t *slist)
-{
- gs_mutex_lock(&slist->mutex);
- gs_countlist_init(&slist->list);
- gs_mutex_unlock(&slist->mutex);
-}
-
-static inline void gs_safelist_add(
- struct gs_safelist_link_t *new, gs_safelist_t *slist)
-{
- gs_mutex_lock(&slist->mutex);
- gs_countlist_add(&new->link, slist->list);
- gs_mutex_unlock(&slist->mutex);
-}
-
-static inline void gs_safelist_add_tail(
- gs_safelist_link_t *new, gs_safelist_t *slist)
-{
- gs_mutex_lock(&slist->mutex);
- gs_countlist_add_tail(&new->link, slist->list);
- gs_mutex_unlock(&slist->mutex);
-}
-
-static inline void gs_safelist_del(
- gs_safelist_link_t *entry, gs_safelist_t *clist)
-{
- gs_mutex_lock(&slist->mutex);
- gs_list_del(&entry->link);
- gs_mutex_unlock(&slist->mutex);
-}
-
-static inline int gs_safelist_empty(gs_safelist_t *slist)
-{
- int empty;
- gs_mutex_lock(&slist->mutex);
- empty = gs_countlist_empty(&slist->list);;
- gs_mutex_unlock(&slist->mutex);
- return empty;
-}
-
-#define gs_safelist_push(_op, _clist) gs_safelist_add_tail(_op, _clist)
-
-static inline gs_safelist_link_t *gs_safelist_pop(gs_safelist_t *list)
-{
- struct gs_safelist_link *entry;
- gs_mutex_lock(&slist->mutex);
- entry = gs_countlist_pop(&list->list);
- gs_mutex_unlock(&slist->mutex);
- return entry;
-}
-
-static inline gs_safelist_link_t *gs_safelist_peek(gs_safelist_t *list)
-{
- gs_safelist_link_t *entry;
- gs_mutex_lock(&list->mutex);
- entry = gs_countlist_peek(&list->list);
- gs_mutex_unlock(&list->mutex);
- return entry;
-}
-
-#define gs_safelist_get_entry(ptr, type, member) \
- gs_countlist_get_entry(ptr, type, member)
-
-#define gs_safelist_link_from_countlist_link(_ptr) \
- gs_countlist_get_entry(_ptr, gs_safelist_link_t, link)
-
-/* these are automatically safe */
-
-#define gs_safelist_for_each(pos, slist) \
- for(gs_mutex_lock(&slist->mutex), \
- struct gs_list_link *lpos = ((slist)->list).list.next, \
- struct gs_list_link *scratch = lpos, \
- pos = gs_list_get_entry(lpos, gs_countlist_link_t, link), \
- gs_mutex_unlock(&slist->mutex); \
- gs_mutex_lock(&slist->mutex) || lpos != &(slist->list).list || gs_mutex_unlock(&slist->mutex); \
- gs_mutex_lock(&slist->mutex), \
- lpos = scratch, \
- scratch = lpos->next, \
- pos = gs_list_get_entry(lpos, gs_countlist_link_t, link), \
- gs_mutex_unlock(&slist->mutex))
-
-#define gs_safelist_for_each_entry(pos, slist, member) \
- for (gs_mutex_lock(struct gs_list_link lpos = ((slist)->list).next, \
- struct gs_list_link *scratch = lpos, \
- pos = gs_countlist_get_entry( \
- gs_list_get_entry(lpos, gs_safelist_link_t, link), \
- typeof(*pos), member); \
- lpos != &(slist)->list; \
- lpos = scratch->next, scratch = lpos->next, \
- pos = gs_countlist_get_entry( \
- gs_list_get_entry(lpos, gs_countlist_link_t, link), \
- typeof(*pos), member))
-
-static inline int gs_safelist_exists(gs_safelist_t *slist, gs_safelist_link_t *llink)
-{
- gs_mutex_lock(&slist->mutex);
- ret = gs_list_exists(&(slist->list.list), llink);
- gs_mutex_unlock(&slist->mutex);
- return ret;
-}
-
-static inline int
-#define gs_countlist_find(clist, compare, ptr) \
- gs_countlist_find(&(clist->list), compare, ptr)
-
-#define gs_countlist_push(__list, __entry) gs_list_push(&(__list)->list, __entry)
-
-#define gs_countlist_pop(__list) gs_list_pop(&(__list)->list)
-
-#define gs_countlist_peek(__list) gs_list_peek(&(__list)->list)
-
-static inline uint64_t gs_countlist_count(gs_countlist_t *list)
-{
- return list->count;
-}
-
-static inline gs_countlist_link_t *gs_countlist_find(
- gs_countlist_t *list,
- int (*compare)(struct gs_countlist_link_t *, void *),
- void *ptr)
-{
- struct gs_countlist_link_t *llink;
- gs_countlist_for_each(llink, list)
- {
- if(compare(llink, list))
- {
- return llink;
- }
- }
- return NULL;
-}
-
-#endif /* __GS_COUNT_LIST_H__ */
diff --git a/code/src/gsl/common/gs-types.h b/code/src/gsl/common/gs-types.h
deleted file mode 100644
index 10feadb..0000000
--- a/code/src/gsl/common/gs-types.h
+++ /dev/null
@@ -1,17 +0,0 @@
-#ifndef __GS_TYPES_H__
-#define __GS_TYPES_H__
-
-#include <stdint.h>
-
-typedef struct { uint64_t l; uint64_t u; } uint128_t;
-
-/**
- * The gs_string_t is a null-terminated string. Used for encoding
- * strings.
- */
-typedef char * gs_string_t;
-
-#include "common/gs-buffer.h"
-#include "common/gs-error.h"
-
-#endif /* __GS_TYPES_H__ */
diff --git a/code/src/gsl/common/gs-hash.h b/code/src/gsl/include/gs-hash.h
similarity index 100%
rename from code/src/gsl/common/gs-hash.h
rename to code/src/gsl/include/gs-hash.h
diff --git a/code/src/gsl/common/gs.h b/code/src/gsl/include/gs.h
similarity index 98%
rename from code/src/gsl/common/gs.h
rename to code/src/gsl/include/gs.h
index f678142..338fa18 100644
--- a/code/src/gsl/common/gs.h
+++ b/code/src/gsl/include/gs.h
@@ -7,6 +7,9 @@
#include "include/gs-list.h"
+#define GS_ERR_MASK (1 << 7)
+#define GS_ECANCELLED (GS_ERR_MASK | 1)
+
#define GS_MAX_RESOURCES 255
#define GS_MAX_CONTEXTS 1024
diff --git a/code/src/gsl/parser/gs-remote-parser.lhs b/code/src/gsl/parser/gs-remote-parser.lhs
index afa3053..9c4c991 100644
--- a/code/src/gsl/parser/gs-remote-parser.lhs
+++ b/code/src/gsl/parser/gs-remote-parser.lhs
@@ -73,7 +73,7 @@ CTypeOfType CDecl NodeInfo
> mkEncodeBlock :: NodeInfo -> Bool -> String -> String -> [CStat]
> mkEncodeBlock ni isPtr typeName fieldName = mkStmtsFromCLines ni $
> "{ \
-> \ ret = gs_encode_"++typeName++"(buf, \""++fieldName++"\", "++(if isPtr then "" else "&")++"x->"++fieldName++"); \
+> \ ret = gs_encode_"++typeName++"(buf, "++fieldName++", "++(if isPtr then "" else "&")++"x->"++fieldName++"); \
> \ if(ret != 0) \
> \ { \
> \ return ret; \
@@ -103,7 +103,7 @@ CTypeOfType CDecl NodeInfo
> mkDecodeBlock :: NodeInfo -> Bool -> String -> String -> [CStat]
> mkDecodeBlock ni isPtr typeName fieldName = mkStmtsFromCLines ni $
> "{ \
-> \ ret = gs_decode_"++typeName++"(buf, \""++fieldName++"\", "++(if isPtr then "" else "&")++"x->"++fieldName++"); \
+> \ ret = gs_decode_"++typeName++"(buf, "++fieldName++", "++(if isPtr then "" else "&")++"x->"++fieldName++"); \
> \ if(ret != 0) \
> \ { \
> \ return ret; \
@@ -133,7 +133,7 @@ CTypeOfType CDecl NodeInfo
> mkSizeBlock :: NodeInfo -> Bool -> String -> String -> [CStat]
> mkSizeBlock ni isPtr typeName fieldName = mkStmtsFromCLines ni $
> "{ \
-> \ size += gs_encode_size_"++typeName++"(\""++fieldName++"\", "++(if isPtr then "" else "&")++"x->"++fieldName++"); \
+> \ size += gs_encode_size_"++typeName++"("++fieldName++", "++(if isPtr then "" else "&")++"x->"++fieldName++"); \
> \}"
> mkSizeStmts :: [CDecl] -> NodeInfo -> RemoteT CStat
@@ -412,7 +412,7 @@ CTypeOfType CDecl NodeInfo
> \ { \
> \ return ret; \
> \ } \
-> \ ret = "++fname++"(\""++inName++"\", &"++outName++"); \
+> \ ret = "++fname++"("++inName++", &"++outName++"); \
> \ if(ret != GS_SUCCESS) \
> \ { \
> \ return ret; \
diff --git a/code/src/gsl/proto/gs-byteswap.h b/code/src/gsl/proto/gs-byteswap.h
deleted file mode 100644
index 4d6e9fc..0000000
--- a/code/src/gsl/proto/gs-byteswap.h
+++ /dev/null
@@ -1,112 +0,0 @@
-/* Macros to swap the order of bytes in integer values.
- Copyright (C) 1997, 1998, 2000, 2001, 2002 Free Software Foundation, Inc.
- This file is part of the GNU C Library.
-
- The GNU C Library is free software; you can redistribute it and/or
- modify it under the terms of the GNU Lesser General Public
- License as published by the Free Software Foundation; either
- version 2.1 of the License, or (at your option) any later version.
-
- The GNU C Library 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
- Lesser General Public License for more details.
-
- You should have received a copy of the GNU Lesser General Public
- License along with the GNU C Library; if not, write to the Free
- Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
- 02111-1307 USA. */
-
-/* Modified by Phil Carns (pcarns(a)parl.clemson.edu)
- * June 2003
- * For use with custom network encoding routines in the BMI component of
- * the Parallel Virtual File System version 2.
- */
-
-#ifndef __GS_BYTESWAP_H
-#define __GS_BYTESWAP_H
-
-#include "gs-config.h"
-
-#ifndef __bswap_16
-/* Swap bytes in 16 bit value. */
-#ifdef __GNUC__
-# define __bswap_16(x) \
- (__extension__ \
- ({ unsigned short int __bsx = (x); \
- ((((__bsx) >> 8) & 0xff) | (((__bsx) & 0xff) << 8)); }))
-#else
-static __inline unsigned short int
-__bswap_16 (unsigned short int __bsx)
-{
- return ((((__bsx) >> 8) & 0xff) | (((__bsx) & 0xff) << 8));
-}
-#endif
-#endif
-
-#ifndef __bswap_32
-/* Swap bytes in 32 bit value. */
-#ifdef __GNUC__
-# define __bswap_32(x) \
- (__extension__ \
- ({ unsigned int __bsx = (x); \
- ((((__bsx) & 0xff000000) >> 24) | (((__bsx) & 0x00ff0000) >> 8) | \
- (((__bsx) & 0x0000ff00) << 8) | (((__bsx) & 0x000000ff) << 24)); }))
-#else
-static __inline unsigned int
-__bswap_32 (unsigned int __bsx)
-{
- return ((((__bsx) & 0xff000000) >> 24) | (((__bsx) & 0x00ff0000) >> 8) |
- (((__bsx) & 0x0000ff00) << 8) | (((__bsx) & 0x000000ff) << 24));
-}
-#endif
-#endif
-
-#ifndef __bswap_64
-#if defined __GNUC__ && __GNUC__ >= 2
-/* Swap bytes in 64 bit value. */
-# define __bswap_constant_64(x) \
- ((((x) & 0xff00000000000000ull) >> 56) \
- | (((x) & 0x00ff000000000000ull) >> 40) \
- | (((x) & 0x0000ff0000000000ull) >> 24) \
- | (((x) & 0x000000ff00000000ull) >> 8) \
- | (((x) & 0x00000000ff000000ull) << 8) \
- | (((x) & 0x0000000000ff0000ull) << 24) \
- | (((x) & 0x000000000000ff00ull) << 40) \
- | (((x) & 0x00000000000000ffull) << 56))
-
-# define __bswap_64(x) \
- (__extension__ \
- ({ union { __extension__ unsigned long long int __ll; \
- unsigned int __l[2]; } __w, __r; \
- if (__builtin_constant_p (x)) \
- __r.__ll = __bswap_constant_64 (x); \
- else \
- { \
- __w.__ll = (x); \
- __r.__l[0] = __bswap_32 (__w.__l[1]); \
- __r.__l[1] = __bswap_32 (__w.__l[0]); \
- } \
- __r.__ll; }))
-#else
-#ifdef WORDS_BIGENDIAN
-#error FIX ME: no 64 bit bswap routine for non GNUC preprocessor.
-#endif
-#endif
-#endif
-
-#ifdef WORDS_BIGENDIAN
-#define gshton16(x) __bswap_16(x)
-#define gshton32(x) __bswap_32(x)
-#define gshton64(x) __bswap_64(x)
-#else
-#define gshton16(x) x
-#define gshton32(x) x
-#define gshton64(x) x
-#endif
-
-#define gsntoh16(x) gshton16(x)
-#define gsntoh32(x) gshton32(x)
-#define gsntoh64(x) gshton64(x)
-
-#endif /* __BMI_BYTESWAP_H */
diff --git a/code/src/gsl/proto/gs-encoding-pw.h b/code/src/gsl/proto/gs-encoding-pw.h
deleted file mode 100644
index c0f9b02..0000000
--- a/code/src/gsl/proto/gs-encoding-pw.h
+++ /dev/null
@@ -1,442 +0,0 @@
-#ifndef __GS_ENCODING_PW_H__
-#define __GS_ENCODING_PW_H__
-
-/*
- * This is an efficient encoding scheme based on Pete Wyckoff's encoding
- * scheme in PVFS. PW's scheme used CPP macros, whereas this one uses
- * inlined functions in order to avoid the headache and hassle that comes
- * with CPP macros (no type checking, can't be debugged properly, etc.), but
- * still gain the performance of inlined code.
- *
- * The encoding scheme rely's on byte swapping everything to little endian
- * in its encoded form. This means little endian machines need to do nothing
- * besides copy data directly to the structure. See gs-byteswap.h.
- *
- * This encoding scheme is used by the GS remote generation code, and is expected
- * to have a specific format and set of encoding/decoding functions for each basic
- * type. The required functions and format are:
- *
- * gs_ret_t gs_encode_<typename>(
- * gs_buffer_t *buf, const gs_string_t varname, <typename> *x);
- *
- * gs_ret_t gs_decode_<typename>(
- * gs_buffer_t *buf, gs_string_t *varname, <typename> *x);
- *
- * uint64_t gs_encode_size_<typename>(const gs_string_t varname, <typename> *x);
- *
- * The varname fields are included in the function signature for other
- * schemes, this scheme does not include variable names (its not self-describing)
- * in its encoding format.
- *
- * Encoding/decoding macros are required for list types, because
- * we need to be able to invoke specific encoding routines for
- * each element of the list without using function pointers.
- * their signatures are slightly different:
- *
- * void gs_encode_<typename>(
- * gs_buffer_t *buf,
- * const gs_string_t varname,
- * <typename> *cx,
- * <element typename>,
- * <element varname>,
- * <element typename>,
- * gs_ret_t *ret);
- *
- * void gs_decode_<typename>(
- * gs_buffer_t *buf,
- * const gs_string_t varname,
- * <typename> *cx,
- * <element typename>,
- * <element varname>,
- * gs_ret_t *ret);
- *
- * gs_ret_t gs_encode_size_<typename>(
- * <typename> *cx,
- * const gs_string_t varname,
- * <element typename>,
- * uint64_t *size);
- *
- * see the GS remote documentation for further info.
- */
-
-#include <assert.h>
-
-#include "common/gs-types.h"
-#include "common/gs-buffer.h"
-#include "proto/gs-byteswap.h"
-
-/* macros used by pw encoding macros - probably shouldn't
- * be used elsewhere
- */
-#define gs_roundup4(x) (((x)+3) & ~3)
-#define gs_roundup8(x) (((x)+7) & ~7)
-
-/* basic encoding types */
-
-/* Type: uint128_t
- *
- * 16 byte unsigned integer. This is an additional type not included
- * in stdint.h. We use it for unique ids (nodes, objects), so we
- * provide encoding/decoding functions here.
- *
- * Format: [VALUE]
- * Bytes: <16>
- */
-static inline uint64_t gs_encode_size_uint128_t(
- const gs_string_t n __unused, uint128_t *x)
-{
- return sizeof(uint128_t);
-}
-static inline gs_ret_t gs_encode_uint128_t(
- gs_buffer_t *buf, const gs_string_t n __unused, uint128_t *x)
-{
- assert(buf);
- assert(x);
- gs_buffer_check_overflow(buf, 16);
- *(uint64_t *) (gs_buffer_cptr(buf)) = gshton64((x)->l);
- gs_buffer_inc(buf, 8);
- *(uint64_t *) (gs_buffer_cptr(buf)) = gshton64((x)->u);
- gs_buffer_inc(buf, 8);
- return GS_SUCCESS;
-}
-static inline gs_ret_t gs_decode_uint128_t(
- gs_buffer_t *buf, const gs_string_t n __unused, uint128_t *x)
-{
- assert(buf);
- assert(x);
- gs_buffer_check_overflow(buf, 16);
- (x)->l = gsntoh64(*(uint64_t *)(gs_buffer_cptr(buf)));
- gs_buffer_inc(buf, 8);
- (x)->u = gsntoh64(*(uint64_t *)(gs_buffer_cptr(buf)));
- gs_buffer_inc(buf, 8);
- return GS_SUCCESS;
-}
-
-/* Type: uint64_t
- *
- * 8 byte unsigned integer
- *
- * Format: [VALUE]
- * Bytes: <8>
- */
-static inline uint64_t gs_encode_size_uint64_t(
- const gs_string_t n __unused, uint64_t *x)
-{
- return sizeof(uint64_t);
-}
-static inline gs_ret_t gs_encode_uint64_t(
- gs_buffer_t *buf, const gs_string_t n __unused, uint64_t *x)
-{
- assert(buf);
- assert(x);
- gs_buffer_check_overflow(buf, 8);
- *(uint64_t *) (gs_buffer_cptr(buf)) = gshton64(*(x));
- gs_buffer_inc(buf, 8);
- return GS_SUCCESS;
-}
-static inline gs_ret_t gs_decode_uint64_t(
- gs_buffer_t *buf, gs_string_t *n __unused, uint64_t *x)
-{
- assert(buf);
- assert(x);
- gs_buffer_check_overflow(buf, 8);
- *(x) = gsntoh64(*(uint64_t*) (gs_buffer_cptr(buf)));
- gs_buffer_inc(buf, 8);
- return GS_SUCCESS;
-}
-
-/* Type: int64_t
- *
- * 8 byte signed integer
- *
- * Format: [VALUE]
- * Bytes: <8>
- */
-static inline uint64_t gs_encode_size_int64_t(
- const gs_string_t n __unused, int64_t *x)
-{
- return sizeof(int64_t);
-}
-static inline gs_ret_t gs_encode_int64_t(
- gs_buffer_t *buf, const gs_string_t n __unused, int64_t *x)
-{
- assert(buf);
- assert(x);
- gs_buffer_check_overflow(buf, 8);
- *(int64_t*) (gs_buffer_cptr(buf)) = gshton64(*(x));
- gs_buffer_inc(buf, 8);
-}
-static inline gs_ret_t gs_decode_int64_t(
- gs_buffer_t *buf, gs_string_t *n __unused, int64_t *x)
-{
- assert(buf);
- assert(x);
- gs_buffer_check_overflow(buf, 8);
- *(x) = gsntoh64(*(int64_t*) (gs_buffer_cptr(buf)));
- gs_buffer_inc(buf, 8);
-}
-
-/* Type: uint32_t
- *
- * 4 byte unsigned integer
- *
- * Format: [VALUE]
- * Bytes: <4><4 byte padding>
- */
-static inline uint64_t gs_encode_size_uint32_t(
- const gs_string_t n __unused, uint32_t *x)
-{
- return sizeof(uint32_t);
-}
-static inline gs_ret_t gs_encode_uint32_t(
- gs_buffer_t *buf, const gs_string_t n __unused, uint32_t *x)
-{
- assert(buf);
- assert(x);
- gs_buffer_check_overflow(buf, 8);
- *(uint32_t*) *(gs_buffer_cptr(buf)) = gshton32(*(x));
- gs_buffer_inc(buf, 8);
-}
-static inline gs_ret_t gs_decode_uint32_t(
- gs_buffer_t *buf, gs_string_t *n __unused, uint32_t *x)
-{
- assert(buf);
- assert(x);
- gs_buffer_check_overflow(buf, 8);
- *(x) = gsntoh32(*(uint32_t*) (gs_buffer_cptr(buf)));
- gs_buffer_inc(buf, 8);
-}
-
-/* Type: int32_t
- *
- * 4 byte signed integer
- *
- * Format: [VALUE]
- * Bytes: <4>
- */
-static inline uint64_t gs_encode_size_int32_t(
- const gs_string_t n __unused, int32_t *x)
-{
- return sizeof(int32_t);
-}
-static inline gs_ret_t gs_encode_int32_t(
- gs_buffer_t *buf, const gs_string_t n __unused, int32_t *x)
-{
- assert(buf);
- assert(x);
- gs_buffer_check_overflow(buf, 8);
- *(int32_t*) (gs_buffer_cptr(buf)) = gshton32(*(x));
- gs_buffer_inc(buf, 8);
-}
-static inline gs_ret_t gs_decode_int32_t(
- gs_buffer_t *buf, gs_string_t *n __unused, int32_t *x)
-{
- assert(buf);
- assert(x);
- gs_buffer_check_overflow(buf, 8);
- *(x) = gsntoh32(*(int32_t*) *(gs_buffer_cptr(buf)));
- gs_buffer_inc(buf, 4);
-}
-
-/* Type: gs_string_t
- *
- * This is a null terminated ASCII string.
- *
- * Format: [LENGTH][STRING][PAD8]
- * Bytes: <4><LENGTH+1><PAD8>
- *
- * Padding is added to the end of the encoded string to make the entire encoding
- * 8-byte aligned. If the string is null or null terminator is the only character,
- * the format changes to [0][0], with a total size of 8.
- */
-static inline uint64_t gs_encode_size_gs_string_t(
- const gs_string_t n __unused, gs_string_t *x)
-{
- uint32_t len = 0;
- if(*x)
- {
- len = strlen(*x);
- return gs_roundup8(4 + len + 1);
- }
- else
- {
- return 8;
- }
-}
-static inline gs_ret_t gs_encode_gs_string_t(
- gs_buffer_t *buf, const gs_string_t n __unused , gs_string_t *x)
-{
- assert(buf);
- assert(x);
- uint32_t len = 0;
- if (*x) len = strlen(*x);
- *(uint32_t *) (gs_buffer_cptr(buf)) = gshton32(len);
- if (len)
- {
- memcpy((gs_buffer_cptr(buf)+4), *x, len+1);
- gs_buffer_inc(buf, gs_roundup8(4 + len + 1));
- }
- else
- {
- *(uint32_t *) (gs_buffer_cptr(buf)+4) = 0;
- gs_buffer_inc(buf, 8);
- }
- return GS_SUCCESS;
-}
-static inline gs_ret_t gs_decode_gs_string_t(
- gs_buffer_t *buf, gs_string_t *n __unused, gs_string_t *x)
-{
- assert(buf);
- assert(x);
- uint32_t len = gsntoh32(*(uint32_t *) (gs_buffer_cptr(buf)));
- *x = (gs_buffer_cptr(buf)+4);
- if (len)
- {
- gs_buffer_inc(buf, roundup8(4 + len + 1));
- }
- else
- {
- gs_buffer_inc(buf, 8);
- }
- return GS_SUCCESS;
-}
-
-/**
- * Type: gs_buffer_t
- *
- * The generic buffer type. An array of bytes and a size.
- * Format: [SIZE][BUFFER]...[PAD8]
- */
-static inline uint64_t gs_encode_size_gs_buffer_t(
- const gs_string_t n __unused, gs_buffer_t *x)
-{
- assert(x);
- if(x->buffer)
- {
- return gs_roundup8(8 + x->size);
- }
- return size;
-}
-
-static inline gs_ret_t gs_encode_gs_buffer_t(
- gs_buffer_t *buffer, gs_string_t n __unused, gs_buffer_t *x)
-{
- gs_ret_t ret;
-
- assert(buffer);
- assert(x);
- gs_buffer_check_overflow(buffer, gs_roundup8(8 + x->size));
- ret = gs_encode_uint64_t(buffer, "size", &x->size);
- if(ret != GS_SUCCESS)
- {
- return ret;
- }
-
- memcpy(gs_buffer_cpr(buffer), x->buffer, x->size);
- gs_buffer_inc(gs_roundup8(x->size));
- return 0;
-}
-
-static inline gs_ret_t gs_decode_gs_buffer_t(
- gs_buffer_t *buffer, gs_string_t n __unused, gs_buffer_t *x)
-{
- gs_ret_t ret;
- uint64_t size;
-
- assert(buffer);
- assert(x);
-
- ret = gs_decode_uint64_t(buffer, &size);
- if(ret != GS_SUCCESS)
- {
- return ret;
- }
- gs_buffer_check_overflow(buffer, gs_roundup8(x->size));
- ret = gs_buffer_alloc(x, size);
- if(ret != GS_SUCCESS)
- {
- return ret;
- }
- memcpy(x->buffer, buffer, x->size);
- gs_buffer_inc(buffer, gs_roundup8(x->size));
- return GS_SUCCESS;
-}
-
-/**
- * Type: gs_error_t
- *
- * The error type. We encode the error An array of bytes and a size.
- * Format: [SIZE][BUFFER]...[PAD8]
- */
-static inline uint64_t gs_encode_size_gs_error_t(
- const gs_string_t n __unused, gs_buffer_t *x)
-{
- assert(x);
- if(x->buffer)
- {
- return gs_roundup8(8 + x->size);
- }
- return size;
-}
-
-/* Type: gs_countlist_t
- *
- * A list of typed structures. Note the gs_list_t type does not keep
- * track of its size, and so only provide encoding functions for the
- * gs_countlist_t type. That should be used where a list is expected to
- * be serialized.
- *
- * Format: [COUNT][ELEM1][ELEM2]...[PAD8]
- * Bytes: <4>
- *
- * Note the size function (macro) is expensive, as we have to calculate the
- * sizes of individual elements. The remote code should avoid using it.
- */
-#define gs_encode_size_gs_countlist_t(__list, __varname, __typename, __size) do { \
- __typename *__pos; \
- __sum = 0; \
- gs_countlist_for_each_entry(__pos, __list) \
- { \
- __sum += gs_encode_size_##__typename(__pos, NULL); \
- } \
- *(__size) = gs_roundup8(8 + __sum); \
-} while(0)
-
-#define gs_encode_gs_countlist_t( \
- __buf, __varname, __list, __typename, __member, __ret) do { \
- __typename *__pos; \
- gs_ret_t mret; \
- mret = gs_encode_uint64_t(__buf, NULL, gs_countlist_count(__list)); \
- if(mret == GS_SUCCESS) \
- { \
- gs_countlist_for_each_entry(__pos, __list, __member) \
- { \
- mret = gs_encode_##__typename(__buf, NULL, __pos); \
- if(mret != GS_SUCCESS) break; \
- } \
- } \
- *(__ret) = mret; \
-} while(0)
-
-#define gs_decode_gs_countlist_t( \
- __buf, __varname, __list, __typename, __member, __ret) do { \
- __typename *__newt; \
- uint64_t i = 0, uint64_t c; \
- gs_ret_t mret; \
- gs_countlist_init(__list); \
- mret = gs_decode_uint64_t(__buf, NULL, &c); \
- if(mret == GS_SUCCESS) \
- { \
- for(; i < c; ++i) \
- { \
- __newt = (__typename *)__buf; \
- mret = gs_decode_##__typename(__buf, NULL, __newt); \
- if(mret != GS_SUCCESS) break; \
- gs_countlist_link_clear(&(__newt)->__member); \
- gs_countlist_add_tail(&(__newt)->__member, __list); \
- } \
- } \
- *(__ret) = mret; \
-} while(0)
-
-#endif /* __GS_ENCODING_PW_H__ */
diff --git a/code/src/gsl/proto/gs-encoding.h b/code/src/gsl/proto/gs-encoding.h
deleted file mode 100644
index e96af66..0000000
--- a/code/src/gsl/proto/gs-encoding.h
+++ /dev/null
@@ -1,7 +0,0 @@
-#ifndef __GS_ENCODING_H__
-#define __GS_ENCODING_H__
-
-/* right now we use the PW encoding scheme */
-#include "proto/gs-encoding-pw.h"
-
-#endif
hooks/post-receive
--
Grayskull Repository
1
0
[Gs-commits] Grayskull Repository branch, master, updated. git-migration-305-g80083cf
by noreply@mcs.anl.gov 17 Dec '09
by noreply@mcs.anl.gov 17 Dec '09
17 Dec '09
A ref change was pushed to the repository containing
the project "Grayskull Repository".
The branch, master has been updated
via 80083cfdfe7b0950eec19f57a6ec12d8774c3351 (commit)
via db391c7a119b49f223bbe33cfa7e03027c63a766 (commit)
from 281aa78117f68ba1bc46ea6213767e56839a05cb (commit)
Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.
- Log -----------------------------------------------------------------
commit 80083cfdfe7b0950eec19f57a6ec12d8774c3351
Author: Samuel Lang <slang(a)bblogin.mcs.anl.gov>
Date: Thu Dec 17 13:41:13 2009 -0600
some type infrastructure for remote encoding/decoding.
commit db391c7a119b49f223bbe33cfa7e03027c63a766
Author: Samuel Lang <slang(a)bblogin.mcs.anl.gov>
Date: Wed Dec 16 16:00:32 2009 -0600
fix examples/rpc-invoke.gs to work with latest shared/private features.
-----------------------------------------------------------------------
Summary of changes:
code/src/gsl/common/gs-buffer.h | 73 +++++
code/src/gsl/common/gs-count-list.h | 126 ++++++++
code/src/gsl/common/gs-debug.h | 16 +
code/src/gsl/common/gs-error.h | 86 ++++++
code/src/gsl/{include => common}/gs-hash.h | 0
code/src/gsl/common/gs-list.h | 230 +++++++++++++++
code/src/gsl/common/gs-node.h | 15 +
code/src/gsl/common/gs-safe-list.h | 161 ++++++++++
code/src/gsl/common/gs-types.h | 17 +
code/src/gsl/common/gs.h | 128 ++++++++
code/src/gsl/include/gs.h | 131 --------
code/src/gsl/parser/CGen.lhs | 4 +
code/src/gsl/parser/gs-blocking-parser.lhs | 17 +-
code/src/gsl/parser/gs-remote-parser.lhs | 8 +-
code/src/gsl/proto/gs-byteswap.h | 112 +++++++
code/src/gsl/proto/gs-encoding-pw.h | 442 ++++++++++++++++++++++++++++
code/src/gsl/proto/gs-encoding.h | 7 +
17 files changed, 1434 insertions(+), 139 deletions(-)
create mode 100644 code/src/gsl/common/gs-buffer.h
create mode 100644 code/src/gsl/common/gs-count-list.h
create mode 100644 code/src/gsl/common/gs-debug.h
create mode 100644 code/src/gsl/common/gs-error.h
rename code/src/gsl/{include => common}/gs-hash.h (100%)
create mode 100644 code/src/gsl/common/gs-list.h
create mode 100644 code/src/gsl/common/gs-node.h
create mode 100644 code/src/gsl/common/gs-safe-list.h
create mode 100644 code/src/gsl/common/gs-types.h
create mode 100644 code/src/gsl/common/gs.h
delete mode 100644 code/src/gsl/include/gs.h
create mode 100644 code/src/gsl/proto/gs-byteswap.h
create mode 100644 code/src/gsl/proto/gs-encoding-pw.h
create mode 100644 code/src/gsl/proto/gs-encoding.h
Diff of changes:
diff --git a/code/src/gsl/common/gs-buffer.h b/code/src/gsl/common/gs-buffer.h
new file mode 100644
index 0000000..5ee944e
--- /dev/null
+++ b/code/src/gsl/common/gs-buffer.h
@@ -0,0 +1,73 @@
+#ifndef __GS_BUFFER_H__
+#define __GS_BUFFER_H__
+
+#include <stdlib.h>
+#ifdef HAVE_MALLOC_H
+#include <malloc.h>
+#endif
+
+#include "common/gs-types.h"
+
+/* We require a max size for a buffer, to prevent clients from requesting
+ * (perhaps due to a bug or bit-flip somewhere) more memory than is available
+ * on the machine.
+ */
+
+/**
+ * The buffer type is used for generic byte streams. A current pointer field
+ * is included allowing the buffer to be used by encoding/decoding mechanisms
+ * before being transmitted. The buffer type can be encoded itself, allowing
+ * it to be used as a generic buffer type.
+ */
+typedef struct
+{
+ void *buffer;
+ uint64_t size;
+ void *cptr;
+} gs_buffer_t;
+
+#define GS_BUFFER_STATIC_INITIALIZER() = { NULL, 0, NULL }
+
+#define gs_buffer_cptr(__buf) ((__buf)->cptr)
+
+static inline gs_ret_t gs_buffer_alloc(gs_buffer_t *buffer, int64_t size)
+{
+ (*buffer)->buffer = malloc(sizeof(*(*buffer)->buffer) * size);
+ if(!(*buffer)->buffer)
+ {
+ return gs_error_errno(ENOMEM);
+ }
+ (*buffer)->size = size;
+ gs_buffer_ptr_reset(buffer);
+ return GS_SUCCESS;
+}
+
+static inline void gs_buffer_free(gs_buffer_t *buffer)
+{
+ if(buffer && buffer->buffer) free(buffer->buffer);
+ buffer->buffer = NULL;
+ buffer->cptr = NULL;
+ buffer->size = 0;
+}
+
+static inline void gs_buffer_ptr_reset(gs_buffer_t *buffer)
+{
+ buffer->cptr = buffer->buffer;
+}
+
+/* The buffer_check_overflow macro verfies that the current buffer pointer is not
+ * at the end of the buffer, and that there's enough space left for __inc bytes.
+ */
+#define gs_buffer_check_overflow(__buf, __inc) do { \
+ if((__buf)->size < (((__buf)->cptr - (__buf)->buffer) + (__inc))) \
+ { \
+ return gs_error_errno(EOVERFLOW); \
+ } \
+} while(0)
+
+/* Increment the current buffer pointer */
+#define gs_buffer_inc(__buf, __inc) do { \
+ (__buf)->cptr+=(__inc); \
+} while(0)
+
+#endif /* __GS_BUFFER_H__ */
diff --git a/code/src/gsl/common/gs-count-list.h b/code/src/gsl/common/gs-count-list.h
new file mode 100644
index 0000000..1aec02c
--- /dev/null
+++ b/code/src/gsl/common/gs-count-list.h
@@ -0,0 +1,126 @@
+#ifndef __GS_COUNT_LIST_H__
+#define __GS_COUNT_LIST_H__
+
+#include "common/gs-list.h"
+
+typedef struct
+{
+ gs_list_t list;
+ uin64_t count;
+} gs_countlist_t;
+
+typedef struct
+{
+ gs_countlist_t *inlist;
+ struct gs_list_link link;
+} gs_countlist_link_t;
+
+#define GS_COUNT_LIST_NULL { { NULL, NULL }, 0 }
+
+#define GS_COUNT_LIST_STATIC_INITIALIZER(name) { { &(name), &(name) }, 0 }
+
+#define GS_COUNT_LIST_DEFINE(name) \
+ gs_countlist_t name = GS_COUNT_LIST_STATIC_INITIALIZER(name)
+
+#define gs_countlist_link_clear(__link) do { \
+ (__link)->inlist = NULL; \
+ gs_list_link_clear(&((__link)->link)); \
+} while(0)
+
+static inline void gs_countlist_init(gs_countlist_t *clist)
+{
+ gs_list_init(&clist->list);
+ clist->count = 0;
+}
+
+static inline void gs_countlist_add(
+ struct gs_countlist_link_t *new, gs_countlist_t *clist)
+{
+ assert(new->inlist == NULL);
+ assert(new->link.next == NULL && new->link.prev == NULL);
+ gs_list_add(&new->link, clist->list);
+ clist->count++;
+}
+
+static inline void gs_countlist_add_tail(
+ gs_countlist_link_t *new, gs_countlist_t *clist)
+{
+ assert(new->inlist == NULL);
+ assert(new->link.next == NULL && new->link.prev == NULL);
+ gs_list_add_tail(&new->link, clist->list);
+ clist->count++;
+}
+
+static inline void gs_countlist_del(
+ gs_countlist_link_t *entry, gs_countlist_t *clist)
+{
+ assert(entry->link.next != NULL && entry->link.prev != NULL);
+ assert(entry->inlist == clist);
+ gs_list_del(&entry->link);
+ clist->count--;
+ CLEAR_GS_LIST_LINK(entry->link);
+}
+
+static inline int gs_countlist_empty(gs_countlist_t *clist)
+{
+ return clist->count == 0;
+}
+
+#define gs_countlist_push(_op, _clist) gs_countlist_add_tail(_op, _clist)
+
+static inline gs_countlist_link_t *gs_countlist_pop(gs_countlist_t *list)
+{
+ struct gs_countlist_link *entry;
+ if(gs_countlist_empty(list)) return NULL;
+ entry = gs_list_get_entry(gs_list_pop(&list->list), gs_countlist_link_t, link);
+ countlist->count--;
+ CLEAR_GS_LIST_LINK(entry);
+ assert(((gs_countlist_t *)entry->inlist) == list);
+ entry->inlist = NULL;
+ return entry;
+}
+
+#define gs_countlist_peek(_list) \
+ gs_list_get_entry(gs_list_peek(&(_list)->list), gs_countlist_link_t, link)
+
+#define gs_countlist_get_entry(ptr, type, member) \
+ gs_list_get_entry(ptr, type, member)
+
+#define gs_countlist_link_from_list_link(_ptr) \
+ gs_list_get_entry(_ptr, gs_countlist_link_t, link)
+
+/* these are automatically safe for removal during iteration */
+
+#define gs_countlist_exists(clist, llink) gs_list_exists(&(clist->list), llink)
+
+#define gs_countlist_find(clist, compare, ptr) \
+ gs_countlist_find(&(clist->list), compare, ptr)
+
+#define gs_countlist_push(__list, __entry) gs_list_push(&(__list)->list, __entry)
+
+#define gs_countlist_pop(__list) gs_list_pop(&(__list)->list)
+
+#define gs_countlist_peek(__list) gs_list_peek(&(__list)->list)
+
+static inline uint64_t gs_countlist_size(gs_countlist_t *list)
+{
+ return list->count;
+}
+
+static inline gs_countlist_link_t *gs_countlist_find(
+ gs_countlist_t *list,
+ int (*compare)(struct gs_countlist_link_t *, void *),
+ void *ptr)
+{
+ struct gs_countlist_link_t *llink;
+ gs_countlist_for_each(llink, list)
+ {
+ if(compare(llink, list))
+ {
+ return llink;
+ }
+ }
+ return NULL;
+}
+
+#endif /* __GS_COUNT_LIST_H__ */
diff --git a/code/src/gsl/common/gs-debug.h b/code/src/gsl/common/gs-debug.h
new file mode 100644
index 0000000..d0e9481
--- /dev/null
+++ b/code/src/gsl/common/gs-debug.h
@@ -0,0 +1,16 @@
+enum gs_debug_mask
+{
+ GS_DEBUG_LEVEL0 = 0,
+ GS_DEBUG_LEVEL1 = 1,
+ GS_DEBUG_LEVEL2 = 2
+};
+
+/**
+ * Debugging is used by developers during development when writing code
+ * and debugging their code in distributed environments. It is not
+ * meant for providing information to end-users.
+ */
+uint32_t gs_debug(enum gs_debug_mask mask,
+ char *message);
+
+
diff --git a/code/src/gsl/common/gs-error.h b/code/src/gsl/common/gs-error.h
new file mode 100644
index 0000000..afe45d0
--- /dev/null
+++ b/code/src/gsl/common/gs-error.h
@@ -0,0 +1,86 @@
+#ifndef __GS_ERROR_H__
+#define __GS_ERROR_H__
+
+#define GS_ERR_MASK (1 << 7)
+#define GS_ECANCELLED (GS_ERR_MASK | 1)
+
+/**
+ * This struct is used internally by the gs_error_t type, defined below.
+ *
+ * The error message adds information useful to the consumer of the error
+ * (the user or administrator). Error messages are tagged with the location
+ * (the node) where the error message was added to the error structure.
+ * Error messages are optional! In order to maintain a lightweight error
+ * interface, error messages should only be added to errors where the error
+ * is clearly an unrecoverable error. The error interfaces provide constructs
+ * both for errors with and without messages.
+ */
+struct gs_error_message
+{
+ gs_node_t location;
+ gs_string_t *message;
+ gs_countlist_link_t link; /* we use countlist to allow for encoding */
+};
+
+/**
+ * The error type allows errors to be wrapped in an error type, useful
+ * for managing error codes, logging errors in a consistent format, and
+ * later finger-pointing of errors. This structure and the
+ * companion error interfaces should be used throughout the entire framework.
+ * Errors in responses should
+ * be in the gs_error_t format, and errors from resources and other components
+ * should use this type as well.
+ * The error structure consists of a single error code for the
+ * error, the source node where the error is generated, and optional error
+ * messages.
+ */
+typedef struct
+{
+ gs_node_t node;
+ int32_t error_code;
+ gs_countlist_t messages;
+} gs_error_t;
+
+typedef gs_error_t gs_ret_t;
+
+#define GS_SUCCESS { GS_NODE_NULL, GS_ERROR_NONE, GS_COUNT_LIST_NULL }
+
+/**
+ * Wrap an error code as a gs_error_t error. This will clear the
+ * other fields in the error, and set the node to the current
+ * node.
+ *
+ * This is a lightweight interface to
+ * construct a gs_error_t type, useful for recoverable errors.
+ */
+void gs_error_wrap(
+ int32_t error_code,
+ gs_error_t *error);
+
+/**
+ * Create a gs_error_t type from an error code, and include a message
+ * about the error. The message gets copied to the resulting error
+ * structure, so it can be freed after the error returns. The returned
+ * error structure is a heap variable, a companion call to gs_error_free
+ * is required.
+ */
+gs_error_t *gs_error_create(
+ int32_t error_code,
+ char *message /** An optional message to add to the error */);
+
+/**
+ * Add a message to the set of error messages within an error structure. This
+ * function allows for finger-pointing and path-following of
+ * errors that pass through multiple nodes. The current node is added
+ * with the message to the stack of messages.
+ */
+void gs_error_add_message(
+ gs_error_t *error,
+ char *message);
+
+/**
+ * Free an error that was created with gs_error_create.
+ */
+void gs_error_destroy(gs_error_t *error);
+
+#endif /* __GS_ERROR_H__ */
diff --git a/code/src/gsl/include/gs-hash.h b/code/src/gsl/common/gs-hash.h
similarity index 100%
rename from code/src/gsl/include/gs-hash.h
rename to code/src/gsl/common/gs-hash.h
diff --git a/code/src/gsl/common/gs-list.h b/code/src/gsl/common/gs-list.h
new file mode 100644
index 0000000..d2dc62f
--- /dev/null
+++ b/code/src/gsl/common/gs-list.h
@@ -0,0 +1,230 @@
+#ifndef __GS_LIST_H__
+#define __GS_LIST_H__
+
+#ifdef __STRICT_ANSI__
+#define inline __inline__
+#endif
+
+#include <stdlib.h>
+#include <assert.h>
+
+typedef struct gs_list_link gs_list_link_t;
+struct gs_list_link {
+ struct gs_list_link *next, *prev;
+};
+
+typedef gs_list_link_t gs_list_t;
+
+#define GS_LIST_STATIC_INITIALIZER(name) { &(name), &(name) }
+
+#define GS_LIST_DEFINE(name) \
+ gs_list_t name = GS_LIST_STATIC_INITIALIZER(name)
+
+static inline void gs_list_init(gs_list_t *list)
+{
+ list->next = (struct gs_list_link *)list;
+ list->prev = (struct gs_list_link *)list;
+}
+
+static inline void gs_list_link_clear(gs_list_link_t *llink)
+{
+ ((struct gs_list_link *)llink)->next = NULL;
+ ((struct gs_list_link *)llink)->prev = NULL;
+}
+
+/*
+ * Insert a new entry between two known consecutive entries.
+ *
+ * This is only for internal gs_list manipulation where we know
+ * the prev/next entries already!
+ */
+static inline void __gs_list_add(struct gs_list_link * new,
+ struct gs_list_link * prev,
+ struct gs_list_link * next)
+{
+ next->prev = new;
+ new->next = next;
+ new->prev = prev;
+ prev->next = new;
+}
+
+/**
+ * gs_list_add - add a new entry
+ * @new: new entry to be added
+ * @head: gs_list head to add it after
+ *
+ * Insert a new entry after the specified head.
+ * This is good for implementing stacks.
+ */
+static inline void gs_list_add(struct gs_list_link *new, gs_list_t *head)
+{
+ __gs_list_add(new, head, head->next);
+}
+
+/**
+ * gs_list_add_tail - add a new entry
+ * @new: new entry to be added
+ * @head: gs_list head to add it before
+ *
+ * Insert a new entry before the specified head.
+ * This is useful for implementing queues.
+ */
+static inline void gs_list_add_tail(struct gs_list_link *new, gs_list_t *head)
+{
+ __gs_list_add(new, head->prev, head);
+}
+
+/*
+ * Delete a gs_list entry by making the prev/next entries
+ * point to each other.
+ *
+ * This is only for internal gs_list manipulation where we know
+ * the prev/next entries already!
+ */
+static inline void __gs_list_del(struct gs_list_link * prev,
+ struct gs_list_link * next)
+{
+ next->prev = prev;
+ prev->next = next;
+}
+
+/**
+ * gs_list_del - deletes entry from gs_list.
+ * @entry: the element to delete from the gs_list.
+ * Note: gs_list_empty on entry does not return true after this, the entry is in an undefined state.
+ */
+static inline void gs_list_del(struct gs_list_link *entry)
+{
+ assert(entry->prev != NULL && entry->next != NULL);
+ __gs_list_del(entry->prev, entry->next);
+ entry->prev = NULL; entry->next = NULL;
+}
+
+/**
+ * gs_list_del_clear - deletes entry from gs_list and reinitialize it.
+ * @entry: the element to delete from the gs_list.
+ */
+static inline void gs_list_del_clear(struct gs_list_link *entry)
+{
+ __gs_list_del(entry->prev, entry->next);
+ gs_list_link_clear(entry);
+}
+
+/**
+ * gs_list_empty - tests whether a gs_list is empty
+ * @head: the gs_list to test.
+ */
+static inline int gs_list_empty(gs_list_t *head)
+{
+ return head->next == head;
+}
+
+/**
+ * gs_list_splice - join two gs_lists
+ * @gs_list: the new gs_list to add.
+ * @head: the place to add it in the first gs_list.
+ */
+static inline void gs_list_splice(gs_list_t *gs_list, struct gs_list_link *llink)
+{
+ struct gs_list_link *first = gs_list->next;
+
+ if (first != gs_list) {
+ struct gs_list_link *last = gs_list->prev;
+ struct gs_list_link *at = llink->next;
+
+ first->prev = llink;
+ llink->next = first;
+
+ last->next = at;
+ at->prev = last;
+ }
+}
+
+/**
+ * gs_list_get_entry - get the struct for this entry
+ * @ptr: the &struct gs_list_link pointer.
+ * @type: the type of the struct this is embedded in.
+ * @member: the name of the gs_list_struct within the struct.
+ */
+#define gs_list_get_entry(ptr, type, member) \
+ ((ptr != NULL) ? ((type *)((char *)(ptr)-(unsigned long)((&((type *)0)->member)))) : NULL)
+
+/**
+ * gs_list_for_each - iterate over a list safe against removal of list entry
+ * @pos: the struct gs_list_link * to use as a loop counter.
+ */
+#define gs_list_for_each(pos, head) \
+ for (struct gs_list_link *scratch = ((struct gs_list_link *)head)->next, \
+ pos = ((struct gs_list_link *)head)->next; \
+ pos != ((struct gs_list_link *)head); \
+ pos = scratch, scratch = pos->next)
+
+/**
+ * gs_list_for_each_entry -
+ * iterate over list of given type safe against removal of list entry
+ * @pos: the type * to use as a loop counter.
+ * @head: the head for your list.
+ * @member: the name of the list_struct within the struct.
+ */
+#define gs_list_for_each_entry(pos, head, member) \
+ for (struct gs_list_link *scratch = (head)->next, \
+ pos = gs_list_get_entry((head)->next, typeof(*pos), member); \
+ pos && (&pos->member != (head)); \
+ pos = gs_list_get_entry(scratch, typeof(*pos), member), \
+ scratch = pos->member.next)
+
+static inline int gs_list_exists(gs_list_t *list, struct gs_list_link *llink)
+{
+ struct gs_list_link *mypos;
+ gs_list_for_each(mypos, list)
+ {
+ if(mypos == llink)
+ {
+ return 1;
+ }
+ }
+ return 0;
+}
+
+static inline struct gs_list_link * gs_list_find(
+ gs_list_t *list,
+ int (*compare)(struct gs_list_link *, void *),
+ void *ptr)
+{
+ struct gs_list_link *pos;
+ gs_list_for_each(pos, list)
+ {
+ if(compare(pos, ptr))
+ {
+ return pos;
+ }
+ }
+ return NULL;
+}
+
+#define gs_list_push(__list, __entry) gs_list_add_tail((__entry), (__list))
+
+static inline struct gs_list_link * gs_list_pop(gs_list_t *list)
+{
+ struct gs_list_link *entry = list->next;
+ if(gs_list_empty(list)) return NULL;
+ gs_list_del(list->next);
+ return entry;
+}
+
+static inline struct gs_list_link *gs_list_peek(gs_list_t *list)
+{
+ if(list->next == list) return NULL;
+ return list->next;
+}
+
+#endif
+
+/*
+ * Local variables:
+ * c-indent-level: 4
+ * c-basic-offset: 4
+ * End:
+ *
+ * vim: ts=8 sts=4 sw=4 expandtab
+ */
diff --git a/code/src/gsl/common/gs-node.h b/code/src/gsl/common/gs-node.h
new file mode 100644
index 0000000..7d3193d
--- /dev/null
+++ b/code/src/gsl/common/gs-node.h
@@ -0,0 +1,15 @@
+#ifndef __GS_NODE_H__
+#define __GS_NODE_H__
+
+#include "common/gs-types.h"
+
+/**
+ * The gs_node_t is an opaque address for a node in the system.
+ */
+typedef uint128_t gs_node_t;
+
+gs_node_t gs_mynode(void);
+
+void gs_set_mynode(gs_node_t node);
+
+#endif /* __GS_NODE_H__ */
diff --git a/code/src/gsl/common/gs-safe-list.h b/code/src/gsl/common/gs-safe-list.h
new file mode 100644
index 0000000..cfc6f1e
--- /dev/null
+++ b/code/src/gsl/common/gs-safe-list.h
@@ -0,0 +1,161 @@
+#ifndef __GS_SAFE_LIST_H__
+#define __GS_SAFE_LIST_H__
+
+#ifdef __STRICT_ANSI__
+/* strict ANSI C doesn't have 'inline' functions, so we use __inline__ instead */
+#define inline __inline__
+#endif
+
+#include "include/gs-count-list.h"
+
+typedef struct
+{
+ gs_countlist_t list;
+ gs_mutex_t mutex;
+} gs_safelist_t;
+
+typedef gs_countlist_link_t gs_safelist_link_t;
+
+#define GS_SAFE_LIST_STATIC_INITIALIZER(name) \
+ { { { &(name), &(name) }, 0 }, GS_MUTEX_INITIALIZER }
+
+#define GS_SAFE_LIST_DEFINE(name) \
+ gs_safelist_t name = GS_SAFE_LIST_STATIC_INITIALIZER(name)
+
+#define gs_safelist_link_clear(__link) do { \
+ gs_list_link_clear(&((__link)->link)); \
+} while(0)
+
+static inline void gs_safelist_init(gs_safelist_t *slist)
+{
+ gs_mutex_lock(&slist->mutex);
+ gs_countlist_init(&slist->list);
+ gs_mutex_unlock(&slist->mutex);
+}
+
+static inline void gs_safelist_add(
+ struct gs_safelist_link_t *new, gs_safelist_t *slist)
+{
+ gs_mutex_lock(&slist->mutex);
+ gs_countlist_add(&new->link, slist->list);
+ gs_mutex_unlock(&slist->mutex);
+}
+
+static inline void gs_safelist_add_tail(
+ gs_safelist_link_t *new, gs_safelist_t *slist)
+{
+ gs_mutex_lock(&slist->mutex);
+ gs_countlist_add_tail(&new->link, slist->list);
+ gs_mutex_unlock(&slist->mutex);
+}
+
+static inline void gs_safelist_del(
+ gs_safelist_link_t *entry, gs_safelist_t *clist)
+{
+ gs_mutex_lock(&slist->mutex);
+ gs_list_del(&entry->link);
+ gs_mutex_unlock(&slist->mutex);
+}
+
+static inline int gs_safelist_empty(gs_safelist_t *slist)
+{
+ int empty;
+ gs_mutex_lock(&slist->mutex);
+ empty = gs_countlist_empty(&slist->list);;
+ gs_mutex_unlock(&slist->mutex);
+ return empty;
+}
+
+#define gs_safelist_push(_op, _clist) gs_safelist_add_tail(_op, _clist)
+
+static inline gs_safelist_link_t *gs_safelist_pop(gs_safelist_t *list)
+{
+ struct gs_safelist_link *entry;
+ gs_mutex_lock(&slist->mutex);
+ entry = gs_countlist_pop(&list->list);
+ gs_mutex_unlock(&slist->mutex);
+ return entry;
+}
+
+static inline gs_safelist_link_t *gs_safelist_peek(gs_safelist_t *list)
+{
+ gs_safelist_link_t *entry;
+ gs_mutex_lock(&list->mutex);
+ entry = gs_countlist_peek(&list->list);
+ gs_mutex_unlock(&list->mutex);
+ return entry;
+}
+
+#define gs_safelist_get_entry(ptr, type, member) \
+ gs_countlist_get_entry(ptr, type, member)
+
+#define gs_safelist_link_from_countlist_link(_ptr) \
+ gs_countlist_get_entry(_ptr, gs_safelist_link_t, link)
+
+/* these are automatically safe */
+
+#define gs_safelist_for_each(pos, slist) \
+ for(gs_mutex_lock(&slist->mutex), \
+ struct gs_list_link *lpos = ((slist)->list).list.next, \
+ struct gs_list_link *scratch = lpos, \
+ pos = gs_list_get_entry(lpos, gs_countlist_link_t, link), \
+ gs_mutex_unlock(&slist->mutex); \
+ gs_mutex_lock(&slist->mutex) || lpos != &(slist->list).list || gs_mutex_unlock(&slist->mutex); \
+ gs_mutex_lock(&slist->mutex), \
+ lpos = scratch, \
+ scratch = lpos->next, \
+ pos = gs_list_get_entry(lpos, gs_countlist_link_t, link), \
+ gs_mutex_unlock(&slist->mutex))
+
+#define gs_safelist_for_each_entry(pos, slist, member) \
+ for (gs_mutex_lock(struct gs_list_link lpos = ((slist)->list).next, \
+ struct gs_list_link *scratch = lpos, \
+ pos = gs_countlist_get_entry( \
+ gs_list_get_entry(lpos, gs_safelist_link_t, link), \
+ typeof(*pos), member); \
+ lpos != &(slist)->list; \
+ lpos = scratch->next, scratch = lpos->next, \
+ pos = gs_countlist_get_entry( \
+ gs_list_get_entry(lpos, gs_countlist_link_t, link), \
+ typeof(*pos), member))
+
+static inline int gs_safelist_exists(gs_safelist_t *slist, gs_safelist_link_t *llink)
+{
+ gs_mutex_lock(&slist->mutex);
+ ret = gs_list_exists(&(slist->list.list), llink);
+ gs_mutex_unlock(&slist->mutex);
+ return ret;
+}
+
+static inline int
+#define gs_countlist_find(clist, compare, ptr) \
+ gs_countlist_find(&(clist->list), compare, ptr)
+
+#define gs_countlist_push(__list, __entry) gs_list_push(&(__list)->list, __entry)
+
+#define gs_countlist_pop(__list) gs_list_pop(&(__list)->list)
+
+#define gs_countlist_peek(__list) gs_list_peek(&(__list)->list)
+
+static inline uint64_t gs_countlist_count(gs_countlist_t *list)
+{
+ return list->count;
+}
+
+static inline gs_countlist_link_t *gs_countlist_find(
+ gs_countlist_t *list,
+ int (*compare)(struct gs_countlist_link_t *, void *),
+ void *ptr)
+{
+ struct gs_countlist_link_t *llink;
+ gs_countlist_for_each(llink, list)
+ {
+ if(compare(llink, list))
+ {
+ return llink;
+ }
+ }
+ return NULL;
+}
+
+#endif /* __GS_COUNT_LIST_H__ */
diff --git a/code/src/gsl/common/gs-types.h b/code/src/gsl/common/gs-types.h
new file mode 100644
index 0000000..10feadb
--- /dev/null
+++ b/code/src/gsl/common/gs-types.h
@@ -0,0 +1,17 @@
+#ifndef __GS_TYPES_H__
+#define __GS_TYPES_H__
+
+#include <stdint.h>
+
+typedef struct { uint64_t l; uint64_t u; } uint128_t;
+
+/**
+ * The gs_string_t is a null-terminated string. Used for encoding
+ * strings.
+ */
+typedef char * gs_string_t;
+
+#include "common/gs-buffer.h"
+#include "common/gs-error.h"
+
+#endif /* __GS_TYPES_H__ */
diff --git a/code/src/gsl/common/gs.h b/code/src/gsl/common/gs.h
new file mode 100644
index 0000000..f678142
--- /dev/null
+++ b/code/src/gsl/common/gs.h
@@ -0,0 +1,128 @@
+#ifndef __GS_H__
+#define __GS_H__
+
+#include <string.h>
+#include <stdint.h>
+#include <assert.h>
+
+#include "include/gs-list.h"
+
+#define GS_MAX_RESOURCES 255
+#define GS_MAX_CONTEXTS 1024
+
+#define GS_RESOURCE_MASK (((uint64_t)0xFF)<<56)
+#define GS_GET_RESOURCE_MASK(resource_id) (GS_RESOURCE_MASK&(((uint64_t)resource_id)<<56))
+#define GS_GET_RESOURCE_ID(op_id) (((op_id&GS_RESOURCE_MASK)>>56)&0xFF)
+
+#ifdef __GS_POSIX_LOCKING__
+#include <pthread.h>
+#endif
+
+typedef enum
+{
+ GS_POSTED = 0,
+ GS_COMPLETE = 1
+} gs_ret_t;
+
+typedef struct gs_hints *gs_hints_t;
+typedef struct gs_context *gs_context_t;
+
+typedef uint64_t gs_op_id_t;
+
+gs_op_id_t gs_id_gen(int resource_id, uint64_t ptr);
+uint64_t gs_id_lookup(gs_op_id_t id, int *resource_id);
+
+#ifdef __GS_POSIX_LOCKING__
+
+typedef pthread_mutex_t gs_mutex_t;
+typedef pthread_mutexattr_t gs_mutexattr_t;
+#define gs_mutex_lock(__mut) pthread_mutex_lock(__mut)
+#define gs_mutex_unlock(__mut) pthread_mutex_unlock(__mut)
+#define gs_mutex_init(__mut, __attr) pthread_mutex_init(__mut, __attr)
+#define GS_MUTEX_INITIALIZER PTHREAD_MUTEX_INITIALIZER
+#define GS_COND_INITIALIZER PTHREAD_COND_INITIALIZER
+
+typedef pthread_cond_t gs_cond_t;
+typedef pthread_condattr_t gs_condattr_t;
+#define gs_cond_init(__cond, __condattr) pthread_cond_init(__cond, __condattr)
+#define gs_cond_signal(__cond) pthread_cond_signal(__cond)
+#define gs_cond_broadcast(__cond) pthread_cond_broadcast(__cond)
+#define gs_cond_wait(__cond, __mutex) pthread_cond_wait(__cond, __mutex)
+#define gs_cond_timedwait(__cond, __mutex, __time) pthread_cond_timedwait(__cond, __mutex, __time)
+#define gs_cond_destroy(__cond) pthread_cond_destroy(__cond)
+
+#else
+
+typedef int gs_mutex_t;
+typedef int gs_mutexattr_t;
+static inline int gs_mutex_lock(gs_mutex_t *__mut) { return 0; }
+static inline int gs_mutex_unlock(gs_mutex_t *__mut) { return 0; }
+static inline int gs_mutex_init(gs_mutex_t *__mut, gs_mutexattr_t *__attr) {return 0; }
+#define GS_MUTEX_INITIALIZER 0
+
+typedef int gs_cond_t;
+typedef int gs_condattr_t;
+#define GS_COND_INITIALIZER 0
+
+static inline int gs_cond_init(gs_cond_t *__cond, gs_condattr_t *__condattr) { return 0; }
+static inline int gs_cond_signal(gs_cond_t *__cond) { return 0; }
+static inline int gs_cond_broadcast(gs_cond_t *__cond) { return 0; }
+static inline int gs_cond_wait(gs_cond_t *__cond, gs_mutex_t *__mutex) { return 0; }
+static inline int gs_cond_timedwait(
+ gs_cond_t *__cond, gs_mutex_t *__mutex, struct timespec *abstime) { return 0; }
+static inline int gs_cond_destroy(gs_cond_t *__cond) { return 0; }
+
+#endif
+
+/* The resource structure is defined by a given resource, and registered
+ * to the gs management code during resource initialization.
+ */
+struct gs_resource
+{
+ const char *resource_name;
+ int (*test)(gs_op_id_t id, int ms_timeout);
+ int (*poll_context)(gs_context_t context, int ms_timeout);
+ int (*cancel)(gs_context_t ctx, gs_op_id_t id);
+ int (*register_context)(gs_context_t context);
+ int (*unregister_context)(gs_context_t context);
+};
+
+/* Called by resources to register themselves to the resource framework */
+int gs_resource_register(struct gs_resource *resource);
+int gs_resource_unregister(int resource_id);
+
+/* Contexts are created to allow separation of polling for different logical
+ * groups of operations.
+ */
+int gs_context_create(gs_context_t *context, int resource_count, ...);
+
+/* Context destruction. Called to cleanup state allocated in gs_context_create.
+ */
+int gs_context_destroy(gs_context_t context);
+
+/* Poll for completion of the operations within the given context up to a
+ * timeout value.
+ */
+int gs_poll(gs_context_t context, int ms);
+
+/* Cancel an operation */
+int gs_cancel_op(gs_context_t context, gs_op_id_t op_id);
+
+#include <sys/time.h>
+
+#define GS_REL_MSECS_TO_ABS_TIMESPEC(__msecs, __abs) \
+ do { \
+ struct timeval __now; \
+ gettimeofday(&__now, NULL); \
+ __abs.tv_sec = __now.tv_sec + (int)(__msecs / 1e3); \
+ __abs.tv_nsec = (__now.tv_usec * 1e3) + ((__msecs % 1000) * 1e6); \
+ if(__abs.tv_nsec >= 1e9) \
+ { \
+ __abs.tv_sec++; \
+ __abs.tv_nsec -= 1e9; \
+ } \
+ } while(0)
+
+#include "gs-internal.h"
+
+#endif
diff --git a/code/src/gsl/include/gs.h b/code/src/gsl/include/gs.h
deleted file mode 100644
index 338fa18..0000000
--- a/code/src/gsl/include/gs.h
+++ /dev/null
@@ -1,131 +0,0 @@
-#ifndef __GS_H__
-#define __GS_H__
-
-#include <string.h>
-#include <stdint.h>
-#include <assert.h>
-
-#include "include/gs-list.h"
-
-#define GS_ERR_MASK (1 << 7)
-#define GS_ECANCELLED (GS_ERR_MASK | 1)
-
-#define GS_MAX_RESOURCES 255
-#define GS_MAX_CONTEXTS 1024
-
-#define GS_RESOURCE_MASK (((uint64_t)0xFF)<<56)
-#define GS_GET_RESOURCE_MASK(resource_id) (GS_RESOURCE_MASK&(((uint64_t)resource_id)<<56))
-#define GS_GET_RESOURCE_ID(op_id) (((op_id&GS_RESOURCE_MASK)>>56)&0xFF)
-
-#ifdef __GS_POSIX_LOCKING__
-#include <pthread.h>
-#endif
-
-typedef enum
-{
- GS_POSTED = 0,
- GS_COMPLETE = 1
-} gs_ret_t;
-
-typedef struct gs_hints *gs_hints_t;
-typedef struct gs_context *gs_context_t;
-
-typedef uint64_t gs_op_id_t;
-
-gs_op_id_t gs_id_gen(int resource_id, uint64_t ptr);
-uint64_t gs_id_lookup(gs_op_id_t id, int *resource_id);
-
-#ifdef __GS_POSIX_LOCKING__
-
-typedef pthread_mutex_t gs_mutex_t;
-typedef pthread_mutexattr_t gs_mutexattr_t;
-#define gs_mutex_lock(__mut) pthread_mutex_lock(__mut)
-#define gs_mutex_unlock(__mut) pthread_mutex_unlock(__mut)
-#define gs_mutex_init(__mut, __attr) pthread_mutex_init(__mut, __attr)
-#define GS_MUTEX_INITIALIZER PTHREAD_MUTEX_INITIALIZER
-#define GS_COND_INITIALIZER PTHREAD_COND_INITIALIZER
-
-typedef pthread_cond_t gs_cond_t;
-typedef pthread_condattr_t gs_condattr_t;
-#define gs_cond_init(__cond, __condattr) pthread_cond_init(__cond, __condattr)
-#define gs_cond_signal(__cond) pthread_cond_signal(__cond)
-#define gs_cond_broadcast(__cond) pthread_cond_broadcast(__cond)
-#define gs_cond_wait(__cond, __mutex) pthread_cond_wait(__cond, __mutex)
-#define gs_cond_timedwait(__cond, __mutex, __time) pthread_cond_timedwait(__cond, __mutex, __time)
-#define gs_cond_destroy(__cond) pthread_cond_destroy(__cond)
-
-#else
-
-typedef int gs_mutex_t;
-typedef int gs_mutexattr_t;
-static inline int gs_mutex_lock(gs_mutex_t *__mut) { return 0; }
-static inline int gs_mutex_unlock(gs_mutex_t *__mut) { return 0; }
-static inline int gs_mutex_init(gs_mutex_t *__mut, gs_mutexattr_t *__attr) {return 0; }
-#define GS_MUTEX_INITIALIZER 0
-
-typedef int gs_cond_t;
-typedef int gs_condattr_t;
-#define GS_COND_INITIALIZER 0
-
-static inline int gs_cond_init(gs_cond_t *__cond, gs_condattr_t *__condattr) { return 0; }
-static inline int gs_cond_signal(gs_cond_t *__cond) { return 0; }
-static inline int gs_cond_broadcast(gs_cond_t *__cond) { return 0; }
-static inline int gs_cond_wait(gs_cond_t *__cond, gs_mutex_t *__mutex) { return 0; }
-static inline int gs_cond_timedwait(
- gs_cond_t *__cond, gs_mutex_t *__mutex, struct timespec *abstime) { return 0; }
-static inline int gs_cond_destroy(gs_cond_t *__cond) { return 0; }
-
-#endif
-
-/* The resource structure is defined by a given resource, and registered
- * to the gs management code during resource initialization.
- */
-struct gs_resource
-{
- const char *resource_name;
- int (*test)(gs_op_id_t id, int ms_timeout);
- int (*poll_context)(gs_context_t context, int ms_timeout);
- int (*cancel)(gs_context_t ctx, gs_op_id_t id);
- int (*register_context)(gs_context_t context);
- int (*unregister_context)(gs_context_t context);
-};
-
-/* Called by resources to register themselves to the resource framework */
-int gs_resource_register(struct gs_resource *resource);
-int gs_resource_unregister(int resource_id);
-
-/* Contexts are created to allow separation of polling for different logical
- * groups of operations.
- */
-int gs_context_create(gs_context_t *context, int resource_count, ...);
-
-/* Context destruction. Called to cleanup state allocated in gs_context_create.
- */
-int gs_context_destroy(gs_context_t context);
-
-/* Poll for completion of the operations within the given context up to a
- * timeout value.
- */
-int gs_poll(gs_context_t context, int ms);
-
-/* Cancel an operation */
-int gs_cancel_op(gs_context_t context, gs_op_id_t op_id);
-
-#include <sys/time.h>
-
-#define GS_REL_MSECS_TO_ABS_TIMESPEC(__msecs, __abs) \
- do { \
- struct timeval __now; \
- gettimeofday(&__now, NULL); \
- __abs.tv_sec = __now.tv_sec + (int)(__msecs / 1e3); \
- __abs.tv_nsec = (__now.tv_usec * 1e3) + ((__msecs % 1000) * 1e6); \
- if(__abs.tv_nsec >= 1e9) \
- { \
- __abs.tv_sec++; \
- __abs.tv_nsec -= 1e9; \
- } \
- } while(0)
-
-#include "gs-internal.h"
-
-#endif
diff --git a/code/src/gsl/parser/CGen.lhs b/code/src/gsl/parser/CGen.lhs
index 0c33963..53f52ed 100644
--- a/code/src/gsl/parser/CGen.lhs
+++ b/code/src/gsl/parser/CGen.lhs
@@ -346,6 +346,10 @@ ctl->params.blah
> (newIdent p1name ni) True ni)
> (newIdent p2name ni) False ni) name False ni
+> addStructPtrPrefixPrefix :: String -> String -> String -> CExpr -> CExpr
+> addStructPtrPrefixPrefix sname p1name p2name (CVar name ni) =
+> CMember (CMember (CMember (CVar (newIdent sname ni) ni) (newIdent p1name ni) True ni) (newIdent p2name ni) True ni) name False ni
+
Take an assign statement, and insert a struct pointer prefix to the lhs. For example:
addStructToAssign "params" "mymem" "funcall(a, 123)"
diff --git a/code/src/gsl/parser/gs-blocking-parser.lhs b/code/src/gsl/parser/gs-blocking-parser.lhs
index 166a9e3..3dcec71 100644
--- a/code/src/gsl/parser/gs-blocking-parser.lhs
+++ b/code/src/gsl/parser/gs-blocking-parser.lhs
@@ -653,6 +653,15 @@ Each callback function defined for a given blocking function must have a unique
> addParams2Prefixes ctlPrefix p1Prefix p2Prefix idents stmt =
> everywhere (mkT $ addParams2PrefixToExpr ctlPrefix p1Prefix p2Prefix idents) stmt
+> addParams2PtrPrefixToExpr :: String -> String -> String -> [Ident] -> CExpr -> CExpr
+> addParams2PtrPrefixToExpr ctlPrefix p1Prefix p2Prefix locals expr
+> | isVarIn locals expr = addStructPtrPrefixPrefix ctlPrefix p1Prefix p2Prefix expr
+> | otherwise = expr
+
+> addParams2PtrPrefixes :: String -> String -> String -> [Ident] -> CStat -> CStat
+> addParams2PtrPrefixes ctlPrefix p1Prefix p2Prefix idents stmts =
+> everywhere (mkT $ addParams2PtrPrefixToExpr ctlPrefix p1Prefix p2Prefix idents) stmts
+
trLocals finds the local declarations for a blocking function context, and translates
the variables used in the statement, into variables prefixed with the ctl and parameter structures.
So for example, if a, b, c and d are local parameters, the statement:
@@ -669,10 +678,10 @@ runfun(ctl->fields.a, ctl->fields.b, ctl->fields.c, ctl->fields.d);
> let pbranchCtx = getPBranchAncestor bctx
> pwaitCtx = getPWaitAncestor bctx
> locals = join $ map getCDeclNames $ getPBranchDecls pbranchCtx
-> in (addParams2Prefixes ctlPrefix
-> (mkPWaitName (getPWaitId pwaitCtx))
-> (mkParamPBranchName (getPBranchId pbranchCtx))
-> locals) stmt
+> in (addParams2PtrPrefixes ctlPrefix
+> ((mkPWaitName (getPWaitId pwaitCtx)) ++ "." ++ mkSharedPtrName)
+> (mkParamPBranchName (getPBranchId pbranchCtx))
+> locals) stmt
> | otherwise = stmt
> trPWaitLocals :: String -> BlockingContext -> CStat -> CStat
diff --git a/code/src/gsl/parser/gs-remote-parser.lhs b/code/src/gsl/parser/gs-remote-parser.lhs
index 9c4c991..afa3053 100644
--- a/code/src/gsl/parser/gs-remote-parser.lhs
+++ b/code/src/gsl/parser/gs-remote-parser.lhs
@@ -73,7 +73,7 @@ CTypeOfType CDecl NodeInfo
> mkEncodeBlock :: NodeInfo -> Bool -> String -> String -> [CStat]
> mkEncodeBlock ni isPtr typeName fieldName = mkStmtsFromCLines ni $
> "{ \
-> \ ret = gs_encode_"++typeName++"(buf, "++fieldName++", "++(if isPtr then "" else "&")++"x->"++fieldName++"); \
+> \ ret = gs_encode_"++typeName++"(buf, \""++fieldName++"\", "++(if isPtr then "" else "&")++"x->"++fieldName++"); \
> \ if(ret != 0) \
> \ { \
> \ return ret; \
@@ -103,7 +103,7 @@ CTypeOfType CDecl NodeInfo
> mkDecodeBlock :: NodeInfo -> Bool -> String -> String -> [CStat]
> mkDecodeBlock ni isPtr typeName fieldName = mkStmtsFromCLines ni $
> "{ \
-> \ ret = gs_decode_"++typeName++"(buf, "++fieldName++", "++(if isPtr then "" else "&")++"x->"++fieldName++"); \
+> \ ret = gs_decode_"++typeName++"(buf, \""++fieldName++"\", "++(if isPtr then "" else "&")++"x->"++fieldName++"); \
> \ if(ret != 0) \
> \ { \
> \ return ret; \
@@ -133,7 +133,7 @@ CTypeOfType CDecl NodeInfo
> mkSizeBlock :: NodeInfo -> Bool -> String -> String -> [CStat]
> mkSizeBlock ni isPtr typeName fieldName = mkStmtsFromCLines ni $
> "{ \
-> \ size += gs_encode_size_"++typeName++"("++fieldName++", "++(if isPtr then "" else "&")++"x->"++fieldName++"); \
+> \ size += gs_encode_size_"++typeName++"(\""++fieldName++"\", "++(if isPtr then "" else "&")++"x->"++fieldName++"); \
> \}"
> mkSizeStmts :: [CDecl] -> NodeInfo -> RemoteT CStat
@@ -412,7 +412,7 @@ CTypeOfType CDecl NodeInfo
> \ { \
> \ return ret; \
> \ } \
-> \ ret = "++fname++"("++inName++", &"++outName++"); \
+> \ ret = "++fname++"(\""++inName++"\", &"++outName++"); \
> \ if(ret != GS_SUCCESS) \
> \ { \
> \ return ret; \
diff --git a/code/src/gsl/proto/gs-byteswap.h b/code/src/gsl/proto/gs-byteswap.h
new file mode 100644
index 0000000..4d6e9fc
--- /dev/null
+++ b/code/src/gsl/proto/gs-byteswap.h
@@ -0,0 +1,112 @@
+/* Macros to swap the order of bytes in integer values.
+ Copyright (C) 1997, 1998, 2000, 2001, 2002 Free Software Foundation, Inc.
+ This file is part of the GNU C Library.
+
+ The GNU C Library is free software; you can redistribute it and/or
+ modify it under the terms of the GNU Lesser General Public
+ License as published by the Free Software Foundation; either
+ version 2.1 of the License, or (at your option) any later version.
+
+ The GNU C Library 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
+ Lesser General Public License for more details.
+
+ You should have received a copy of the GNU Lesser General Public
+ License along with the GNU C Library; if not, write to the Free
+ Software Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
+ 02111-1307 USA. */
+
+/* Modified by Phil Carns (pcarns(a)parl.clemson.edu)
+ * June 2003
+ * For use with custom network encoding routines in the BMI component of
+ * the Parallel Virtual File System version 2.
+ */
+
+#ifndef __GS_BYTESWAP_H
+#define __GS_BYTESWAP_H
+
+#include "gs-config.h"
+
+#ifndef __bswap_16
+/* Swap bytes in 16 bit value. */
+#ifdef __GNUC__
+# define __bswap_16(x) \
+ (__extension__ \
+ ({ unsigned short int __bsx = (x); \
+ ((((__bsx) >> 8) & 0xff) | (((__bsx) & 0xff) << 8)); }))
+#else
+static __inline unsigned short int
+__bswap_16 (unsigned short int __bsx)
+{
+ return ((((__bsx) >> 8) & 0xff) | (((__bsx) & 0xff) << 8));
+}
+#endif
+#endif
+
+#ifndef __bswap_32
+/* Swap bytes in 32 bit value. */
+#ifdef __GNUC__
+# define __bswap_32(x) \
+ (__extension__ \
+ ({ unsigned int __bsx = (x); \
+ ((((__bsx) & 0xff000000) >> 24) | (((__bsx) & 0x00ff0000) >> 8) | \
+ (((__bsx) & 0x0000ff00) << 8) | (((__bsx) & 0x000000ff) << 24)); }))
+#else
+static __inline unsigned int
+__bswap_32 (unsigned int __bsx)
+{
+ return ((((__bsx) & 0xff000000) >> 24) | (((__bsx) & 0x00ff0000) >> 8) |
+ (((__bsx) & 0x0000ff00) << 8) | (((__bsx) & 0x000000ff) << 24));
+}
+#endif
+#endif
+
+#ifndef __bswap_64
+#if defined __GNUC__ && __GNUC__ >= 2
+/* Swap bytes in 64 bit value. */
+# define __bswap_constant_64(x) \
+ ((((x) & 0xff00000000000000ull) >> 56) \
+ | (((x) & 0x00ff000000000000ull) >> 40) \
+ | (((x) & 0x0000ff0000000000ull) >> 24) \
+ | (((x) & 0x000000ff00000000ull) >> 8) \
+ | (((x) & 0x00000000ff000000ull) << 8) \
+ | (((x) & 0x0000000000ff0000ull) << 24) \
+ | (((x) & 0x000000000000ff00ull) << 40) \
+ | (((x) & 0x00000000000000ffull) << 56))
+
+# define __bswap_64(x) \
+ (__extension__ \
+ ({ union { __extension__ unsigned long long int __ll; \
+ unsigned int __l[2]; } __w, __r; \
+ if (__builtin_constant_p (x)) \
+ __r.__ll = __bswap_constant_64 (x); \
+ else \
+ { \
+ __w.__ll = (x); \
+ __r.__l[0] = __bswap_32 (__w.__l[1]); \
+ __r.__l[1] = __bswap_32 (__w.__l[0]); \
+ } \
+ __r.__ll; }))
+#else
+#ifdef WORDS_BIGENDIAN
+#error FIX ME: no 64 bit bswap routine for non GNUC preprocessor.
+#endif
+#endif
+#endif
+
+#ifdef WORDS_BIGENDIAN
+#define gshton16(x) __bswap_16(x)
+#define gshton32(x) __bswap_32(x)
+#define gshton64(x) __bswap_64(x)
+#else
+#define gshton16(x) x
+#define gshton32(x) x
+#define gshton64(x) x
+#endif
+
+#define gsntoh16(x) gshton16(x)
+#define gsntoh32(x) gshton32(x)
+#define gsntoh64(x) gshton64(x)
+
+#endif /* __BMI_BYTESWAP_H */
diff --git a/code/src/gsl/proto/gs-encoding-pw.h b/code/src/gsl/proto/gs-encoding-pw.h
new file mode 100644
index 0000000..c0f9b02
--- /dev/null
+++ b/code/src/gsl/proto/gs-encoding-pw.h
@@ -0,0 +1,442 @@
+#ifndef __GS_ENCODING_PW_H__
+#define __GS_ENCODING_PW_H__
+
+/*
+ * This is an efficient encoding scheme based on Pete Wyckoff's encoding
+ * scheme in PVFS. PW's scheme used CPP macros, whereas this one uses
+ * inlined functions in order to avoid the headache and hassle that comes
+ * with CPP macros (no type checking, can't be debugged properly, etc.), but
+ * still gain the performance of inlined code.
+ *
+ * The encoding scheme rely's on byte swapping everything to little endian
+ * in its encoded form. This means little endian machines need to do nothing
+ * besides copy data directly to the structure. See gs-byteswap.h.
+ *
+ * This encoding scheme is used by the GS remote generation code, and is expected
+ * to have a specific format and set of encoding/decoding functions for each basic
+ * type. The required functions and format are:
+ *
+ * gs_ret_t gs_encode_<typename>(
+ * gs_buffer_t *buf, const gs_string_t varname, <typename> *x);
+ *
+ * gs_ret_t gs_decode_<typename>(
+ * gs_buffer_t *buf, gs_string_t *varname, <typename> *x);
+ *
+ * uint64_t gs_encode_size_<typename>(const gs_string_t varname, <typename> *x);
+ *
+ * The varname fields are included in the function signature for other
+ * schemes, this scheme does not include variable names (its not self-describing)
+ * in its encoding format.
+ *
+ * Encoding/decoding macros are required for list types, because
+ * we need to be able to invoke specific encoding routines for
+ * each element of the list without using function pointers.
+ * their signatures are slightly different:
+ *
+ * void gs_encode_<typename>(
+ * gs_buffer_t *buf,
+ * const gs_string_t varname,
+ * <typename> *cx,
+ * <element typename>,
+ * <element varname>,
+ * <element typename>,
+ * gs_ret_t *ret);
+ *
+ * void gs_decode_<typename>(
+ * gs_buffer_t *buf,
+ * const gs_string_t varname,
+ * <typename> *cx,
+ * <element typename>,
+ * <element varname>,
+ * gs_ret_t *ret);
+ *
+ * gs_ret_t gs_encode_size_<typename>(
+ * <typename> *cx,
+ * const gs_string_t varname,
+ * <element typename>,
+ * uint64_t *size);
+ *
+ * see the GS remote documentation for further info.
+ */
+
+#include <assert.h>
+
+#include "common/gs-types.h"
+#include "common/gs-buffer.h"
+#include "proto/gs-byteswap.h"
+
+/* macros used by pw encoding macros - probably shouldn't
+ * be used elsewhere
+ */
+#define gs_roundup4(x) (((x)+3) & ~3)
+#define gs_roundup8(x) (((x)+7) & ~7)
+
+/* basic encoding types */
+
+/* Type: uint128_t
+ *
+ * 16 byte unsigned integer. This is an additional type not included
+ * in stdint.h. We use it for unique ids (nodes, objects), so we
+ * provide encoding/decoding functions here.
+ *
+ * Format: [VALUE]
+ * Bytes: <16>
+ */
+static inline uint64_t gs_encode_size_uint128_t(
+ const gs_string_t n __unused, uint128_t *x)
+{
+ return sizeof(uint128_t);
+}
+static inline gs_ret_t gs_encode_uint128_t(
+ gs_buffer_t *buf, const gs_string_t n __unused, uint128_t *x)
+{
+ assert(buf);
+ assert(x);
+ gs_buffer_check_overflow(buf, 16);
+ *(uint64_t *) (gs_buffer_cptr(buf)) = gshton64((x)->l);
+ gs_buffer_inc(buf, 8);
+ *(uint64_t *) (gs_buffer_cptr(buf)) = gshton64((x)->u);
+ gs_buffer_inc(buf, 8);
+ return GS_SUCCESS;
+}
+static inline gs_ret_t gs_decode_uint128_t(
+ gs_buffer_t *buf, const gs_string_t n __unused, uint128_t *x)
+{
+ assert(buf);
+ assert(x);
+ gs_buffer_check_overflow(buf, 16);
+ (x)->l = gsntoh64(*(uint64_t *)(gs_buffer_cptr(buf)));
+ gs_buffer_inc(buf, 8);
+ (x)->u = gsntoh64(*(uint64_t *)(gs_buffer_cptr(buf)));
+ gs_buffer_inc(buf, 8);
+ return GS_SUCCESS;
+}
+
+/* Type: uint64_t
+ *
+ * 8 byte unsigned integer
+ *
+ * Format: [VALUE]
+ * Bytes: <8>
+ */
+static inline uint64_t gs_encode_size_uint64_t(
+ const gs_string_t n __unused, uint64_t *x)
+{
+ return sizeof(uint64_t);
+}
+static inline gs_ret_t gs_encode_uint64_t(
+ gs_buffer_t *buf, const gs_string_t n __unused, uint64_t *x)
+{
+ assert(buf);
+ assert(x);
+ gs_buffer_check_overflow(buf, 8);
+ *(uint64_t *) (gs_buffer_cptr(buf)) = gshton64(*(x));
+ gs_buffer_inc(buf, 8);
+ return GS_SUCCESS;
+}
+static inline gs_ret_t gs_decode_uint64_t(
+ gs_buffer_t *buf, gs_string_t *n __unused, uint64_t *x)
+{
+ assert(buf);
+ assert(x);
+ gs_buffer_check_overflow(buf, 8);
+ *(x) = gsntoh64(*(uint64_t*) (gs_buffer_cptr(buf)));
+ gs_buffer_inc(buf, 8);
+ return GS_SUCCESS;
+}
+
+/* Type: int64_t
+ *
+ * 8 byte signed integer
+ *
+ * Format: [VALUE]
+ * Bytes: <8>
+ */
+static inline uint64_t gs_encode_size_int64_t(
+ const gs_string_t n __unused, int64_t *x)
+{
+ return sizeof(int64_t);
+}
+static inline gs_ret_t gs_encode_int64_t(
+ gs_buffer_t *buf, const gs_string_t n __unused, int64_t *x)
+{
+ assert(buf);
+ assert(x);
+ gs_buffer_check_overflow(buf, 8);
+ *(int64_t*) (gs_buffer_cptr(buf)) = gshton64(*(x));
+ gs_buffer_inc(buf, 8);
+}
+static inline gs_ret_t gs_decode_int64_t(
+ gs_buffer_t *buf, gs_string_t *n __unused, int64_t *x)
+{
+ assert(buf);
+ assert(x);
+ gs_buffer_check_overflow(buf, 8);
+ *(x) = gsntoh64(*(int64_t*) (gs_buffer_cptr(buf)));
+ gs_buffer_inc(buf, 8);
+}
+
+/* Type: uint32_t
+ *
+ * 4 byte unsigned integer
+ *
+ * Format: [VALUE]
+ * Bytes: <4><4 byte padding>
+ */
+static inline uint64_t gs_encode_size_uint32_t(
+ const gs_string_t n __unused, uint32_t *x)
+{
+ return sizeof(uint32_t);
+}
+static inline gs_ret_t gs_encode_uint32_t(
+ gs_buffer_t *buf, const gs_string_t n __unused, uint32_t *x)
+{
+ assert(buf);
+ assert(x);
+ gs_buffer_check_overflow(buf, 8);
+ *(uint32_t*) *(gs_buffer_cptr(buf)) = gshton32(*(x));
+ gs_buffer_inc(buf, 8);
+}
+static inline gs_ret_t gs_decode_uint32_t(
+ gs_buffer_t *buf, gs_string_t *n __unused, uint32_t *x)
+{
+ assert(buf);
+ assert(x);
+ gs_buffer_check_overflow(buf, 8);
+ *(x) = gsntoh32(*(uint32_t*) (gs_buffer_cptr(buf)));
+ gs_buffer_inc(buf, 8);
+}
+
+/* Type: int32_t
+ *
+ * 4 byte signed integer
+ *
+ * Format: [VALUE]
+ * Bytes: <4>
+ */
+static inline uint64_t gs_encode_size_int32_t(
+ const gs_string_t n __unused, int32_t *x)
+{
+ return sizeof(int32_t);
+}
+static inline gs_ret_t gs_encode_int32_t(
+ gs_buffer_t *buf, const gs_string_t n __unused, int32_t *x)
+{
+ assert(buf);
+ assert(x);
+ gs_buffer_check_overflow(buf, 8);
+ *(int32_t*) (gs_buffer_cptr(buf)) = gshton32(*(x));
+ gs_buffer_inc(buf, 8);
+}
+static inline gs_ret_t gs_decode_int32_t(
+ gs_buffer_t *buf, gs_string_t *n __unused, int32_t *x)
+{
+ assert(buf);
+ assert(x);
+ gs_buffer_check_overflow(buf, 8);
+ *(x) = gsntoh32(*(int32_t*) *(gs_buffer_cptr(buf)));
+ gs_buffer_inc(buf, 4);
+}
+
+/* Type: gs_string_t
+ *
+ * This is a null terminated ASCII string.
+ *
+ * Format: [LENGTH][STRING][PAD8]
+ * Bytes: <4><LENGTH+1><PAD8>
+ *
+ * Padding is added to the end of the encoded string to make the entire encoding
+ * 8-byte aligned. If the string is null or null terminator is the only character,
+ * the format changes to [0][0], with a total size of 8.
+ */
+static inline uint64_t gs_encode_size_gs_string_t(
+ const gs_string_t n __unused, gs_string_t *x)
+{
+ uint32_t len = 0;
+ if(*x)
+ {
+ len = strlen(*x);
+ return gs_roundup8(4 + len + 1);
+ }
+ else
+ {
+ return 8;
+ }
+}
+static inline gs_ret_t gs_encode_gs_string_t(
+ gs_buffer_t *buf, const gs_string_t n __unused , gs_string_t *x)
+{
+ assert(buf);
+ assert(x);
+ uint32_t len = 0;
+ if (*x) len = strlen(*x);
+ *(uint32_t *) (gs_buffer_cptr(buf)) = gshton32(len);
+ if (len)
+ {
+ memcpy((gs_buffer_cptr(buf)+4), *x, len+1);
+ gs_buffer_inc(buf, gs_roundup8(4 + len + 1));
+ }
+ else
+ {
+ *(uint32_t *) (gs_buffer_cptr(buf)+4) = 0;
+ gs_buffer_inc(buf, 8);
+ }
+ return GS_SUCCESS;
+}
+static inline gs_ret_t gs_decode_gs_string_t(
+ gs_buffer_t *buf, gs_string_t *n __unused, gs_string_t *x)
+{
+ assert(buf);
+ assert(x);
+ uint32_t len = gsntoh32(*(uint32_t *) (gs_buffer_cptr(buf)));
+ *x = (gs_buffer_cptr(buf)+4);
+ if (len)
+ {
+ gs_buffer_inc(buf, roundup8(4 + len + 1));
+ }
+ else
+ {
+ gs_buffer_inc(buf, 8);
+ }
+ return GS_SUCCESS;
+}
+
+/**
+ * Type: gs_buffer_t
+ *
+ * The generic buffer type. An array of bytes and a size.
+ * Format: [SIZE][BUFFER]...[PAD8]
+ */
+static inline uint64_t gs_encode_size_gs_buffer_t(
+ const gs_string_t n __unused, gs_buffer_t *x)
+{
+ assert(x);
+ if(x->buffer)
+ {
+ return gs_roundup8(8 + x->size);
+ }
+ return size;
+}
+
+static inline gs_ret_t gs_encode_gs_buffer_t(
+ gs_buffer_t *buffer, gs_string_t n __unused, gs_buffer_t *x)
+{
+ gs_ret_t ret;
+
+ assert(buffer);
+ assert(x);
+ gs_buffer_check_overflow(buffer, gs_roundup8(8 + x->size));
+ ret = gs_encode_uint64_t(buffer, "size", &x->size);
+ if(ret != GS_SUCCESS)
+ {
+ return ret;
+ }
+
+ memcpy(gs_buffer_cpr(buffer), x->buffer, x->size);
+ gs_buffer_inc(gs_roundup8(x->size));
+ return 0;
+}
+
+static inline gs_ret_t gs_decode_gs_buffer_t(
+ gs_buffer_t *buffer, gs_string_t n __unused, gs_buffer_t *x)
+{
+ gs_ret_t ret;
+ uint64_t size;
+
+ assert(buffer);
+ assert(x);
+
+ ret = gs_decode_uint64_t(buffer, &size);
+ if(ret != GS_SUCCESS)
+ {
+ return ret;
+ }
+ gs_buffer_check_overflow(buffer, gs_roundup8(x->size));
+ ret = gs_buffer_alloc(x, size);
+ if(ret != GS_SUCCESS)
+ {
+ return ret;
+ }
+ memcpy(x->buffer, buffer, x->size);
+ gs_buffer_inc(buffer, gs_roundup8(x->size));
+ return GS_SUCCESS;
+}
+
+/**
+ * Type: gs_error_t
+ *
+ * The error type. We encode the error An array of bytes and a size.
+ * Format: [SIZE][BUFFER]...[PAD8]
+ */
+static inline uint64_t gs_encode_size_gs_error_t(
+ const gs_string_t n __unused, gs_buffer_t *x)
+{
+ assert(x);
+ if(x->buffer)
+ {
+ return gs_roundup8(8 + x->size);
+ }
+ return size;
+}
+
+/* Type: gs_countlist_t
+ *
+ * A list of typed structures. Note the gs_list_t type does not keep
+ * track of its size, and so only provide encoding functions for the
+ * gs_countlist_t type. That should be used where a list is expected to
+ * be serialized.
+ *
+ * Format: [COUNT][ELEM1][ELEM2]...[PAD8]
+ * Bytes: <4>
+ *
+ * Note the size function (macro) is expensive, as we have to calculate the
+ * sizes of individual elements. The remote code should avoid using it.
+ */
+#define gs_encode_size_gs_countlist_t(__list, __varname, __typename, __size) do { \
+ __typename *__pos; \
+ __sum = 0; \
+ gs_countlist_for_each_entry(__pos, __list) \
+ { \
+ __sum += gs_encode_size_##__typename(__pos, NULL); \
+ } \
+ *(__size) = gs_roundup8(8 + __sum); \
+} while(0)
+
+#define gs_encode_gs_countlist_t( \
+ __buf, __varname, __list, __typename, __member, __ret) do { \
+ __typename *__pos; \
+ gs_ret_t mret; \
+ mret = gs_encode_uint64_t(__buf, NULL, gs_countlist_count(__list)); \
+ if(mret == GS_SUCCESS) \
+ { \
+ gs_countlist_for_each_entry(__pos, __list, __member) \
+ { \
+ mret = gs_encode_##__typename(__buf, NULL, __pos); \
+ if(mret != GS_SUCCESS) break; \
+ } \
+ } \
+ *(__ret) = mret; \
+} while(0)
+
+#define gs_decode_gs_countlist_t( \
+ __buf, __varname, __list, __typename, __member, __ret) do { \
+ __typename *__newt; \
+ uint64_t i = 0, uint64_t c; \
+ gs_ret_t mret; \
+ gs_countlist_init(__list); \
+ mret = gs_decode_uint64_t(__buf, NULL, &c); \
+ if(mret == GS_SUCCESS) \
+ { \
+ for(; i < c; ++i) \
+ { \
+ __newt = (__typename *)__buf; \
+ mret = gs_decode_##__typename(__buf, NULL, __newt); \
+ if(mret != GS_SUCCESS) break; \
+ gs_countlist_link_clear(&(__newt)->__member); \
+ gs_countlist_add_tail(&(__newt)->__member, __list); \
+ } \
+ } \
+ *(__ret) = mret; \
+} while(0)
+
+#endif /* __GS_ENCODING_PW_H__ */
diff --git a/code/src/gsl/proto/gs-encoding.h b/code/src/gsl/proto/gs-encoding.h
new file mode 100644
index 0000000..e96af66
--- /dev/null
+++ b/code/src/gsl/proto/gs-encoding.h
@@ -0,0 +1,7 @@
+#ifndef __GS_ENCODING_H__
+#define __GS_ENCODING_H__
+
+/* right now we use the PW encoding scheme */
+#include "proto/gs-encoding-pw.h"
+
+#endif
hooks/post-receive
--
Grayskull Repository
1
0
[Gs-commits] Grayskull Repository branch, master, updated. git-migration-303-g281aa78
by noreply@mcs.anl.gov 16 Dec '09
by noreply@mcs.anl.gov 16 Dec '09
16 Dec '09
A ref change was pushed to the repository containing
the project "Grayskull Repository".
The branch, master has been updated
via 281aa78117f68ba1bc46ea6213767e56839a05cb (commit)
via 47fff9f0f804d326028e856e447c5d43b6df2323 (commit)
via f0af59bef14edfc76999ef6ae50e26ab9629b8be (commit)
from 14c57e23348aff2afda7709a05298029bb724ab4 (commit)
Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.
- Log -----------------------------------------------------------------
commit 281aa78117f68ba1bc46ea6213767e56839a05cb
Author: Phil Carns <carns(a)mcs.anl.gov>
Date: Wed Dec 16 16:09:25 2009 -0500
whitespace fixes
commit 47fff9f0f804d326028e856e447c5d43b6df2323
Author: Phil Carns <carns(a)mcs.anl.gov>
Date: Wed Dec 16 16:06:01 2009 -0500
fix operation ordering in cosd benchmark
commit f0af59bef14edfc76999ef6ae50e26ab9629b8be
Author: Phil Carns <carns(a)mcs.anl.gov>
Date: Wed Dec 16 15:56:07 2009 -0500
preliminary db deadlock handling in cosd
-----------------------------------------------------------------------
Summary of changes:
.../gsl/resources/cosd-prototype/cosd-prototype.c | 106 ++++++++++++++++++--
.../cosd-prototype/test/cosd-bench-concurrent.gs | 15 ++--
2 files changed, 103 insertions(+), 18 deletions(-)
Diff of changes:
diff --git a/code/src/gsl/resources/cosd-prototype/cosd-prototype.c b/code/src/gsl/resources/cosd-prototype/cosd-prototype.c
index 0bfa578..dfda80e 100644
--- a/code/src/gsl/resources/cosd-prototype/cosd-prototype.c
+++ b/code/src/gsl/resources/cosd-prototype/cosd-prototype.c
@@ -467,7 +467,7 @@ int gs_cosd_init(enum progress_mode mode, const char* path)
return(-1);
}
- /* have db do lock detection and reject txn with fewest locks */
+ /* have db do deadlock detection and reject txn with fewest locks */
ret = envp->set_lk_detect(envp, DB_LOCK_MINWRITE);
if(ret != 0)
{
@@ -771,6 +771,7 @@ static int write_op_worker(struct gs_op* op)
COSD_INIT_DBT(key, c_op->u.write.oid);
COSD_INIT_DBT(value, global_log_offset);
+write_op_txn:
/* read log offset from db */
ret = envp->txn_begin(envp, NULL, &txn, 0);
if(ret != 0)
@@ -783,6 +784,10 @@ static int write_op_worker(struct gs_op* op)
ret = log_offset_dbp->get(log_offset_dbp, txn, &key, &value, 0);
if(ret != 0)
{
+ txn->abort(txn);
+ if(ret == DB_LOCK_DEADLOCK)
+ goto write_op_txn;
+
/* TODO: error handling */
c_op->error_code = -1;
return(1);
@@ -791,6 +796,10 @@ static int write_op_worker(struct gs_op* op)
ret = txn->commit(txn, 0);
if(ret != 0)
{
+ txn->abort(txn);
+ if(ret == DB_LOCK_DEADLOCK)
+ goto write_op_txn;
+
/* TODO: error handling */
assert(0);
}
@@ -864,6 +873,7 @@ static int write_op_worker(struct gs_op* op)
*
* dumps all db information from cosd
*/
+/* TODO: audit for deadlocks */
static int dump_op_worker(struct gs_op* op)
{
struct cosd_op *c_op;
@@ -983,6 +993,7 @@ static int dump_op_worker(struct gs_op* op)
*
* creates an object
*/
+/* TODO: audit for deadlocks */
static int create_op_worker(struct gs_op* op)
{
struct cosd_op *c_op;
@@ -1229,6 +1240,7 @@ int gs_cosd_txn_open(uint64_t oid, uint64_t txn_number)
*
* retrieves the current version number of an object
*/
+/* TODO: audit for deadlocks */
static int get_version_op_worker(struct gs_op* op)
{
struct cosd_op *c_op;
@@ -1371,6 +1383,19 @@ static int txn_close_op_worker(struct gs_op* op)
gs_list_del(&txn_acc->hash_link);
gs_mutex_unlock(&txn_mutex);
+txn_close_op_retry:
+ on_disk_count = 0;
+ done = 0;
+ c_get_flag = DB_SET_RANGE;
+ /* clear up on disk list in case this is a retry */
+ gs_list_for_each_safe(iterator, scratch, &on_disk_entries)
+ {
+ tmp_entry = gs_list_get_entry(iterator, struct
+ logical_map_entry, list_link);
+ gs_list_del(&tmp_entry->list_link);
+ free(tmp_entry);
+ }
+
/* do db stuff */
ret = envp->txn_begin(envp, NULL, &txn, 0);
if(ret != 0)
@@ -1385,6 +1410,9 @@ static int txn_close_op_worker(struct gs_op* op)
ret = log_map_dbp->cursor(log_map_dbp, txn, &dbc_p, 0);
if(ret != 0)
{
+ txn->abort(txn);
+ if(ret == DB_LOCK_DEADLOCK)
+ goto txn_close_op_retry;
/* TODO: error handling */
assert(0);
}
@@ -1414,6 +1442,9 @@ static int txn_close_op_worker(struct gs_op* op)
}
if(ret != 0)
{
+ txn->abort(txn);
+ if(ret == DB_LOCK_DEADLOCK)
+ goto txn_close_op_retry;
/* TODO: err handling */
assert(0);
}
@@ -1445,12 +1476,23 @@ static int txn_close_op_worker(struct gs_op* op)
ret = dbc_p->c_del(dbc_p, 0);
if(ret != 0)
{
+ txn->abort(txn);
+ if(ret == DB_LOCK_DEADLOCK)
+ goto txn_close_op_retry;
/* TODO: err handling */
assert(0);
}
}
}
- dbc_p->c_close(dbc_p);
+ ret = dbc_p->c_close(dbc_p);
+ if(ret != 0)
+ {
+ txn->abort(txn);
+ if(ret == DB_LOCK_DEADLOCK)
+ goto txn_close_op_retry;
+ /* TODO: error handling */
+ assert(0);
+ }
/* merge on disk and txn regions */
ret = merge_logical_map(&on_disk_entries, on_disk_count,
@@ -1472,6 +1514,10 @@ static int txn_close_op_worker(struct gs_op* op)
ret = log_map_dbp->put(log_map_dbp, txn, &key, &value, 0);
if(ret != 0)
{
+ txn->abort(txn);
+ free(free_ptr);
+ if(ret == DB_LOCK_DEADLOCK)
+ goto txn_close_op_retry;
/* TODO: err handling */
assert(0);
}
@@ -1485,6 +1531,10 @@ static int txn_close_op_worker(struct gs_op* op)
ret = ver_dbp->get(ver_dbp, txn, &key, &value, 0);
if(ret != 0)
{
+ txn->abort(txn);
+ if(ret == DB_LOCK_DEADLOCK)
+ goto txn_close_op_retry;
+
/* TODO: error handling */
assert(0);
}
@@ -1506,6 +1556,9 @@ static int txn_close_op_worker(struct gs_op* op)
ret = missing_ver_dbp->put(missing_ver_dbp, txn, &mv_key, &mv_value, 0);
if(ret != 0)
{
+ txn->abort(txn);
+ if(ret == DB_LOCK_DEADLOCK)
+ goto txn_close_op_retry;
/* TODO: error handling */
assert(0);
}
@@ -1518,6 +1571,9 @@ static int txn_close_op_worker(struct gs_op* op)
ret = ver_dbp->put(ver_dbp, txn, &key, &value, 0);
if(ret != 0)
{
+ txn->abort(txn);
+ if(ret == DB_LOCK_DEADLOCK)
+ goto txn_close_op_retry;
/* TODO: error handling */
assert(0);
}
@@ -1534,6 +1590,17 @@ static int txn_close_op_worker(struct gs_op* op)
/* delete from db db */
ret = missing_ver_dbp->del(missing_ver_dbp, txn, &mv_key, 0);
+ if(ret == DB_LOCK_DEADLOCK)
+ {
+ txn->abort(txn);
+ goto txn_close_op_retry;
+ }
+ if(ret != 0 && ret != DB_NOTFOUND)
+ {
+ txn->abort(txn);
+ /* TODO: error handling */
+ assert(0);
+ }
}
/* flush current log offset to db in the same txn */
@@ -1547,19 +1614,41 @@ static int txn_close_op_worker(struct gs_op* op)
ret = log_offset_dbp->put(log_offset_dbp, txn, &key, &value, 0);
if(ret != 0)
{
+ txn->abort(txn);
+ if(ret == DB_LOCK_DEADLOCK)
+ goto txn_close_op_retry;
+
/* TODO: error handling */
- c_op->error_code = -1;
- return(1);
+ assert(0);
}
gs_mutex_unlock(&global_log_mutex);
ret = txn->commit(txn, 0);
if(ret != 0)
{
+ txn->abort(txn);
+ if(ret == DB_LOCK_DEADLOCK)
+ goto txn_close_op_retry;
+
/* TODO: error handling */
assert(0);
}
+ gs_list_for_each_safe(iterator, scratch, &on_disk_entries)
+ {
+ tmp_entry = gs_list_get_entry(iterator, struct
+ logical_map_entry, list_link);
+ gs_list_del(&tmp_entry->list_link);
+ free(tmp_entry);
+ }
+ gs_list_for_each_safe(iterator, scratch, &txn_acc->update_list)
+ {
+ tmp_entry = gs_list_get_entry(iterator, struct
+ logical_map_entry, list_link);
+ gs_list_del(&tmp_entry->list_link);
+ free(tmp_entry);
+ }
+
free(txn_acc);
c_op->error_code = 0;
return(1);
@@ -1607,9 +1696,8 @@ gs_ret_t (* gs_cosd_txn_close)(
/* merge_logical_map()
*
- * merges two logical maps into one map. The two input maps are destroyed
- * by this function. The output map is allocated from scratch and can be
- * freed via the free_ptr argument.
+ * merges two logical maps into one map. The output map is allocated from
+ * scratch and can be freed via the free_ptr argument.
*
* returns 0 on success, -errno on failure
*/
@@ -1650,10 +1738,8 @@ static int merge_logical_map(struct gs_list_link* list1_in, int
{
tmp_entry = gs_list_get_entry(iterator, struct logical_map_entry,
list_link);
- gs_list_del(&tmp_entry->list_link);
list1_array[i] = *tmp_entry;
i++;
- free(tmp_entry);
}
assert(i==list1_count);
i=0;
@@ -1661,10 +1747,8 @@ static int merge_logical_map(struct gs_list_link* list1_in, int
{
tmp_entry = gs_list_get_entry(iterator, struct logical_map_entry,
list_link);
- gs_list_del(&tmp_entry->list_link);
list2_array[i] = *tmp_entry;
i++;
- free(tmp_entry);
}
assert(i==list2_count);
diff --git a/code/src/gsl/resources/cosd-prototype/test/cosd-bench-concurrent.gs b/code/src/gsl/resources/cosd-prototype/test/cosd-bench-concurrent.gs
index 7a9de2a..3be7aed 100644
--- a/code/src/gsl/resources/cosd-prototype/test/cosd-bench-concurrent.gs
+++ b/code/src/gsl/resources/cosd-prototype/test/cosd-bench-concurrent.gs
@@ -7,7 +7,7 @@
/* TODO: this needs to be in a header somewhere */
#ifndef llu
-#if SIZEOF_LONG_INT == 4
+#if SIZEOF_LONG_INT == 4
# define llu(x) (x)
# define lld(x) (x)
# define SCANF_lld lld
@@ -76,7 +76,7 @@ static __blocking int do_cosd_test(void)
struct bench_op* tmp_op;
int b_ret;
/* TODO: make buffer size configurable, and check that
- * nothing in workload desc is bigger than this
+ * nothing in workload desc is bigger than this
*/
int64_t buffer_size = 4*1024*1024;
@@ -93,7 +93,6 @@ static __blocking int do_cosd_test(void)
list_link);
/* only writes for now */
assert(tmp_op->type == WRITE);
-
ret = gs_cosd_txn_open(1, b_version);
if(ret != 0)
{
@@ -125,8 +124,10 @@ static __blocking int do_cosd_test(void)
}
}
+#if 0
ret = gs_cosd_dump();
assert(ret == 0);
+#endif
return 0;
}
@@ -180,7 +181,7 @@ int main(int argc, char *argv[])
{
if(line[0] == '#')
continue;
-#if SIZEOF_LONG_INT == 4
+#if SIZEOF_LONG_INT == 4
ret = sscanf(line, "%s %lld %lld", op_string, &offset, &size);
#else
ret = sscanf(line, "%s %ld %ld", op_string, &offset, &size);
@@ -198,7 +199,7 @@ int main(int argc, char *argv[])
tmp_op->type = WRITE;
tmp_op->offset = offset;
tmp_op->size = size;
- gs_list_add(&tmp_op->list_link, &op_list);
+ gs_list_add_tail(&tmp_op->list_link, &op_list);
}
fclose(desc);
@@ -206,7 +207,7 @@ int main(int argc, char *argv[])
printf("# Initializing cosd in poll-driven mode.\n");
else
printf("# Initializing cosd in thread-per-op mode.\n");
-
+
gs_cosd_init(mode, argv[3]);
gs_context_create(&ctx, 1, "cosd");
@@ -218,7 +219,7 @@ int main(int argc, char *argv[])
pc++;
gs_poll(ctx, 10000);
}
-
+
gs_cosd_finalize();
gs_context_destroy(ctx);
return 0;
hooks/post-receive
--
Grayskull Repository
1
0
[Gs-commits] Grayskull Repository branch, master, updated. git-migration-300-g14c57e2
by noreply@mcs.anl.gov 16 Dec '09
by noreply@mcs.anl.gov 16 Dec '09
16 Dec '09
A ref change was pushed to the repository containing
the project "Grayskull Repository".
The branch, master has been updated
via 14c57e23348aff2afda7709a05298029bb724ab4 (commit)
via c201e3128f4e2dd9937a44e438e80d21fc313eb5 (commit)
via 7a41b641fa45571ce3b3a062462f7fa97d198f7f (commit)
via 8b61ad032514fbdfd308ae707a3e819e5bed7176 (commit)
via 1d7b0a46e4952414efd090a985b0517386b1d300 (commit)
from 633a91e55dab62f2552b52e311b721ed6c097985 (commit)
Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.
- Log -----------------------------------------------------------------
commit 14c57e23348aff2afda7709a05298029bb724ab4
Merge: c201e3128f4e2dd9937a44e438e80d21fc313eb5 633a91e55dab62f2552b52e311b721ed6c097985
Author: Samuel Lang <slang(a)bblogin.mcs.anl.gov>
Date: Wed Dec 16 14:58:33 2009 -0600
Merge branch 'master' of login3.mcs.anl.gov:~dkimpe/git/grayskull
commit c201e3128f4e2dd9937a44e438e80d21fc313eb5
Author: Samuel Lang <slang(a)bblogin.mcs.anl.gov>
Date: Wed Dec 16 14:57:31 2009 -0600
fix for pbranch bug found with parallelfor2.gs
commit 7a41b641fa45571ce3b3a062462f7fa97d198f7f
Author: Samuel Lang <slang(a)bblogin.mcs.anl.gov>
Date: Wed Dec 16 13:28:56 2009 -0600
fixed directory entries
commit 8b61ad032514fbdfd308ae707a3e819e5bed7176
Author: Samuel Lang <slang(a)bblogin.mcs.anl.gov>
Date: Wed Dec 16 13:27:20 2009 -0600
basic remote parser.
commit 1d7b0a46e4952414efd090a985b0517386b1d300
Author: Samuel Lang <slang(a)bblogin.mcs.anl.gov>
Date: Wed Dec 16 13:15:24 2009 -0600
Adding basic remote functionality.
This commit adds some functionality for generating stubs/skeletons using the __remote specifier.
-----------------------------------------------------------------------
Summary of changes:
code/src/gsl/.gitignore | 5 +
code/src/gsl/Makefile.in | 12 +-
code/src/gsl/README | 2 +-
code/src/gsl/configure.in | 3 +
code/src/gsl/include/gs-internal.h | 9 +
code/src/gsl/maint/hs/language-c.patch | 98 +++-
code/src/gsl/parser/BlockingContext.lhs | 12 +-
code/src/gsl/parser/CGen.lhs | 41 +-
code/src/gsl/parser/CParse.lhs | 97 ++++-
.../{gs-parser.lhs => gs-blocking-parser.lhs} | 183 +++++---
code/src/gsl/parser/gs-remote-parser.lhs | 518 ++++++++++++++++++++
code/src/gsl/parser/module.mk.in | 12 +-
code/src/gsl/tests/correctness/funptrs.gs | 35 ++
code/src/gsl/tests/correctness/module.mk.in | 5 +-
14 files changed, 911 insertions(+), 121 deletions(-)
create mode 100644 code/src/gsl/.gitignore
rename code/src/gsl/parser/{gs-parser.lhs => gs-blocking-parser.lhs} (90%)
create mode 100644 code/src/gsl/parser/gs-remote-parser.lhs
Diff of changes:
diff --git a/code/src/gsl/.gitignore b/code/src/gsl/.gitignore
new file mode 100644
index 0000000..571af37
--- /dev/null
+++ b/code/src/gsl/.gitignore
@@ -0,0 +1,5 @@
+aclocal.m4
+autom4te.cache
+build
+configure
+maint/hs/GHC
diff --git a/code/src/gsl/Makefile.in b/code/src/gsl/Makefile.in
index 26aac5d..24169b7 100644
--- a/code/src/gsl/Makefile.in
+++ b/code/src/gsl/Makefile.in
@@ -176,6 +176,9 @@ modlibs = $(MODLIBS_$(call canonname,$(1))) \
MODLIBS_GS = $(call modlibs,$(patsubst %.o,%.gs,$(1)))
MODLIBS_C = $(call modlibs,$(patsubst %.o,%.c,$(1)))
+modname = $(MODNAME_$(call canonname,$(1))) \
+ $(MODNAME_$(patsubst $(srcdir)/%,%,$(1)))
+
modcc = $(if $(MODCC_$(1)), \
$(MODCC_$(1)),$(CC))
@@ -265,12 +268,12 @@ $(GSOBJS): %.o: %.gs.s
$(CFLAGS) $(CWARNS) -Wno-redundant-decls $(call MODCFLAGS_GS,$<) $<
$(GSOBJS_INTERM): %.gs.s: %.gs.i parser
- $(E)$(builddir)/parser/gs-parser -o $@ -r $*.gs $(GSPRETTY) $*.gs.i
+ $(E)$(builddir)/parser/gs-blocking-parser -o $@ -r $*.gs $(GSPRETTY) $*.gs.i
$(GSOBJS_DUMMY): %.gs.dummyobj: %.gs
$(Q) " GSCC $*"
$(E)$(call MCC_GS,$<) -D__blocking="" \
- -Dpwait="while(0)" -Dpbranch="" -Dpbreak="break"\
+ -Dpwait="while(0)" -Dpbranch="" -Dpbreak="break" -Dpprivate="" -Dpshared=""\
-I$(srcdir)/include/ -x c -c -o $@ $(LIBCFLAGS) \
-Wall -Wno-implicit -Wno-unused -Werror \
$(CFLAGS) $(call MODCFLAGS_GS,$<) $<
@@ -285,7 +288,7 @@ $(GSTRHDR_CPP): %.gsh.i: %.gsh
$(LIBCFLAGS) $(CFLAGS) $(CWARNS) $(call MODCFLAGS_GS,$<) $(srcdir)/$*.gsh
$(GSTRHDR): %.h: %.gsh.i parser
- $(E)$(builddir)/parser/gs-parser -j -r $(srcdir)/$*.gsh -o $@ $<
+ $(E)$(builddir)/parser/gs-blocking-parser -j -r $(srcdir)/$*.gsh -o $@ $<
$(LIBOBJS): %.o: %.d
$(Q) " CC $@"
@@ -311,7 +314,8 @@ $(HSBIN): %: %.lhs $(HSSRC)
$(E)$(GHC) -odir $(call canonname,$<) \
-hidir $(call canonname,$<) \
-o $@ \
- -i$(call dir,$<) -ilanguage-c-0.3.1/src --make $<
+ -main-is $(call modname,$<) \
+ -i$(call dir,$<) --make $<
LIBRARIES=lib/libgs.a lib/libgstest.a
diff --git a/code/src/gsl/README b/code/src/gsl/README
index e57faf2..c720212 100644
--- a/code/src/gsl/README
+++ b/code/src/gsl/README
@@ -10,9 +10,9 @@ On debian/ubuntu, run (requires sudo privs):
On systems without haskell binary packages, you'll need to do:
* Download/Build/Install ghc from http://www.haskell.org/ghc/
+* Download/Build/Install MTL from http://hackage.haskell.org/cgi-bin/hackage-scripts/package/mtl
* Download/Build/Install happy from http://www.haskell.org/happy/
* Download/Build/Install alex from http://www.haskell.org/alex/
-* Download/Build/Install MTL from http://hackage.haskell.org/cgi-bin/hackage-scripts/package/mtl
* Then run: setup-langc
diff --git a/code/src/gsl/configure.in b/code/src/gsl/configure.in
index 77768cb..aef0cb8 100644
--- a/code/src/gsl/configure.in
+++ b/code/src/gsl/configure.in
@@ -28,7 +28,10 @@ AC_PROG_INSTALL
AC_PROG_CC
AC_PROG_CPP
+AC_C_BIGENDIAN
+
AC_CHECK_SIZEOF([long int])
+AC_CHECK_SIZEOF(void *)
AC_MSG_CHECKING([for required gcc])
if test "x$GCC" = "x"; then
diff --git a/code/src/gsl/include/gs-internal.h b/code/src/gsl/include/gs-internal.h
index 7b2893b..36a3319 100644
--- a/code/src/gsl/include/gs-internal.h
+++ b/code/src/gsl/include/gs-internal.h
@@ -1,6 +1,15 @@
#ifndef __GS_INTERNAL_H__
#define __GS_INTERNAL_H__
+#ifdef __STRICT_ANSI__
+/* strict ANSI C doesn't have 'inline' functions, so we use __inline__ instead */
+#define inline __inline__ __attribute__((flatten))
+#endif
+
+#ifndef __unused
+#define __unused __attribute__((unused))
+#endif
+
/* The gs_ctl structure is used by the gsl generated code to manage parallel and
* nested operations. This structure is not needed by resource writers or gsl
* code.
diff --git a/code/src/gsl/maint/hs/language-c.patch b/code/src/gsl/maint/hs/language-c.patch
index e07dbde..9f7ccb5 100644
--- a/code/src/gsl/maint/hs/language-c.patch
+++ b/code/src/gsl/maint/hs/language-c.patch
@@ -1,6 +1,6 @@
diff -Naur language-c-0.3.3/language-c.cabal language-c-0.3.3-new/language-c.cabal
--- language-c-0.3.3/language-c.cabal 2009-07-02 14:11:45.000000000 -0500
-+++ language-c-0.3.3-new/language-c.cabal 2009-07-07 13:08:11.000000000 -0500
++++ language-c-0.3.3-new/language-c.cabal 2009-12-15 09:16:28.275537558 -0600
@@ -1,4 +1,4 @@
-Name: language-c
+Name: language-gsl
@@ -28,7 +28,7 @@ diff -Naur language-c-0.3.3/language-c.cabal language-c-0.3.3-new/language-c.cab
Extra-Source-Files: AUTHORS AUTHORS.c2hs ChangeLog README
diff -Naur language-c-0.3.3/src/Language/C/Data/Position.hs language-c-0.3.3-new/src/Language/C/Data/Position.hs
--- language-c-0.3.3/src/Language/C/Data/Position.hs 2009-07-02 14:11:45.000000000 -0500
-+++ language-c-0.3.3-new/src/Language/C/Data/Position.hs 2009-07-07 13:11:58.000000000 -0500
++++ language-c-0.3.3-new/src/Language/C/Data/Position.hs 2009-12-15 09:16:28.277945977 -0600
@@ -50,7 +50,7 @@
show BuiltinPosition = "<builtin>"
show InternalPosition = "<internal>"
@@ -40,40 +40,46 @@ diff -Naur language-c-0.3.3/src/Language/C/Data/Position.hs language-c-0.3.3-new
position :: Int -> String -> Int -> Int -> Position
diff -Naur language-c-0.3.3/src/Language/C/Parser/Lexer.x language-c-0.3.3-new/src/Language/C/Parser/Lexer.x
--- language-c-0.3.3/src/Language/C/Parser/Lexer.x 2009-07-02 14:11:45.000000000 -0500
-+++ language-c-0.3.3-new/src/Language/C/Parser/Lexer.x 2009-07-07 13:08:11.000000000 -0500
-@@ -351,6 +351,10 @@
++++ language-c-0.3.3-new/src/Language/C/Parser/Lexer.x 2009-12-15 09:16:28.280809877 -0600
+@@ -351,6 +351,13 @@
idkwtok ('v' : 'o' : 'l' : 'a' : 't' : 'i' : 'l' : 'e' : []) = tok 8 CTokVolatile
idkwtok ('_' : '_' : 'v' : 'o' : 'l' : 'a' : 't' : 'i' : 'l' : 'e' : '_' : '_' : []) = tok 12 CTokVolatile
idkwtok ('w' : 'h' : 'i' : 'l' : 'e' : []) = tok 5 CTokWhile
+idkwtok ('_':'_':'b':'l':'o':'c':'k':'i':'n':'g':[]) = tok 10 CTokBlocking
++idkwtok ('_':'_':'r':'e':'m':'o':'t':'e':[]) = tok 10 CTokRemote
+idkwtok ('p':'w':'a':'i':'t':[]) = tok 5 CTokPWait
+idkwtok ('p':'b':'r':'a':'n':'c':'h':[]) = tok 7 CTokPBranch
+idkwtok ('p':'b':'r':'e':'a':'k':[]) = tok 6 CTokPBreak
++idkwtok ('p':'p':'r':'i':'v':'a':'t':'e':[]) = tok 6 CTokPPrivate
++idkwtok ('p':'s':'h':'a':'r':'e':'d':[]) = tok 6 CTokPShared
idkwtok cs = \pos -> do
name <- getNewName
diff -Naur language-c-0.3.3/src/Language/C/Parser/Parser.y language-c-0.3.3-new/src/Language/C/Parser/Parser.y
--- language-c-0.3.3/src/Language/C/Parser/Parser.y 2009-07-02 14:11:45.000000000 -0500
-+++ language-c-0.3.3-new/src/Language/C/Parser/Parser.y 2009-07-07 13:08:11.000000000 -0500
-@@ -217,6 +217,7 @@
++++ language-c-0.3.3-new/src/Language/C/Parser/Parser.y 2009-12-15 09:16:28.286135310 -0600
+@@ -217,6 +217,8 @@
typedef { CTokTypedef _ }
typeof { CTokTypeof _ }
"__thread" { CTokThread _ }
+"__blocking" { CTokBlocking _ }
++"__remote" { CTokRemote _ }
union { CTokUnion _ }
unsigned { CTokUnsigned _ }
void { CTokVoid _ }
-@@ -236,6 +237,9 @@
+@@ -236,6 +238,11 @@
"__builtin_va_arg" { CTokGnuC GnuCVaArg _ }
"__builtin_offsetof" { CTokGnuC GnuCOffsetof _ }
"__builtin_types_compatible_p" { CTokGnuC GnuCTyCompat _ }
+pwait { CTokPWait _ }
+pbranch { CTokPBranch _ }
+pbreak { CTokPBreak _ }
++pshared { CTokPShared _ }
++pprivate { CTokPPrivate _ }
%%
-@@ -359,6 +363,7 @@
+@@ -359,6 +366,7 @@
| iteration_statement { $1 }
| jump_statement { $1 }
| asm_statement {% withNodeInfo $1 (CAsm $1) }
@@ -81,7 +87,7 @@ diff -Naur language-c-0.3.3/src/Language/C/Parser/Parser.y language-c-0.3.3-new/
-- parse C labeled statement (C99 6.8.1)
-@@ -473,6 +478,16 @@
+@@ -473,6 +481,16 @@
| for '(' enter_scope declaration expression_opt ';' expression_opt ')' statement leave_scope
{% withNodeInfo $1 $ CFor (Right $4) $5 $7 $9 }
@@ -98,44 +104,72 @@ diff -Naur language-c-0.3.3/src/Language/C/Parser/Parser.y language-c-0.3.3-new/
-- parse C jump statement (C99 6.8.6)
--
-@@ -1188,6 +1203,7 @@
+@@ -550,7 +568,7 @@
+ -- storage class and type qualifier
+ ---------------------------------------------------------------------------------------------------------------
+ attr :- __attribute__((..))
+-storage_class :- typedef | extern | static | auto | register | __thread
++storage_class :- typedef | extern | static | auto | register | __thread | __blocking | pprivate | ppshared
+ type_qualifier :- const | volatile | restrict | inline
+ type_qualifier_list :- type_qualifier+
+
+@@ -755,7 +773,7 @@
+
+
+ -- A mixture of type qualifiers (const, volatile, restrict, inline) and storage class specifiers
+--- (extern, static, auto, register, __thread), in any order, but containing at least one storage class specifier.
++-- (extern, static, auto, register, __thread, __blocking, pshared, pprivate), in any order, but containing at least one storage class specifier.
+ --
+ -- declaration_qualifier_list :- <permute> type_qualifier* storage_class+
+ --
+@@ -1188,6 +1206,10 @@
| volatile {% withNodeInfo $1 $ CVolatQual }
| restrict {% withNodeInfo $1 $ CRestrQual }
| inline {% withNodeInfo $1 $ CInlineQual }
+ | "__blocking" {% withNodeInfo $1 $ CBlocking }
++ | "__remote" {% withNodeInfo $1 $ CRemote }
++ | pshared {% withNodeInfo $1 $ CPShared }
++ | pprivate {% withNodeInfo $1 $ CPPrivate }
-- a list containing at least one type_qualifier (const, volatile, restrict, inline)
-- and additionally CAttrs
diff -Naur language-c-0.3.3/src/Language/C/Parser/Tokens.hs language-c-0.3.3-new/src/Language/C/Parser/Tokens.hs
--- language-c-0.3.3/src/Language/C/Parser/Tokens.hs 2009-07-02 14:11:45.000000000 -0500
-+++ language-c-0.3.3-new/src/Language/C/Parser/Tokens.hs 2009-07-07 13:08:11.000000000 -0500
-@@ -132,6 +132,10 @@
++++ language-c-0.3.3-new/src/Language/C/Parser/Tokens.hs 2009-12-15 09:16:28.289379739 -0600
+@@ -132,6 +132,13 @@
| CTokTyIdent !PosLength !Ident -- `typedef-name' identifier
| CTokGnuC !GnuCTok !PosLength -- special GNU C tokens
| CTokEof -- end of file
+ | CTokBlocking !PosLength -- '__blocking'
++ | CTokRemote !PosLength -- '__remote'
+ | CTokPWait !PosLength -- `pwait'
+ | CTokPBranch !PosLength -- `pbranch'
+ | CTokPBreak !PosLength -- `pbreak'
++ | CTokPShared !PosLength -- `pshared'
++ | CTokPPrivate !PosLength -- `pprivate'
-- special tokens used in GNU C extensions to ANSI C
--
-@@ -242,6 +246,10 @@
+@@ -242,6 +249,13 @@
posLenOfTok (CTokIdent pos _) = pos
posLenOfTok (CTokTyIdent pos _) = pos
posLenOfTok (CTokGnuC _ pos ) = pos
+posLenOfTok (CTokBlocking pos ) = pos
++posLenOfTok (CTokRemote pos ) = pos
+posLenOfTok (CTokPWait pos ) = pos
+posLenOfTok (CTokPBranch pos ) = pos
+posLenOfTok (CTokPBreak pos ) = pos
++posLenOfTok (CTokPPrivate pos ) = pos
++posLenOfTok (CTokPShared pos ) = pos
posLenOfTok CTokEof = error "tokenPos: Eof"
instance Show CToken where
-@@ -327,11 +335,15 @@
+@@ -327,11 +341,18 @@
showsPrec _ (CTokTypedef _ ) = showString "typedef"
showsPrec _ (CTokTypeof _ ) = showString "typeof"
showsPrec _ (CTokThread _ ) = showString "__thread"
+ showsPrec _ (CTokBlocking _ ) = showString "__blocking"
++ showsPrec _ (CTokRemote _ ) = showString "__remote"
showsPrec _ (CTokUnion _ ) = showString "union"
showsPrec _ (CTokUnsigned _ ) = showString "unsigned"
showsPrec _ (CTokVoid _ ) = showString "void"
@@ -144,12 +178,14 @@ diff -Naur language-c-0.3.3/src/Language/C/Parser/Tokens.hs language-c-0.3.3-new
+ showsPrec _ (CTokPWait _ ) = showString "pwait"
+ showsPrec _ (CTokPBranch _ ) = showString "pbranch"
+ showsPrec _ (CTokPBreak _ ) = showString "pbreak"
++ showsPrec _ (CTokPPrivate _ ) = showString "pprivate"
++ showsPrec _ (CTokPShared _ ) = showString "pshared"
showsPrec _ (CTokCLit _ c) = shows c
showsPrec _ (CTokILit _ i) = shows i
showsPrec _ (CTokFLit _ f) = shows f
diff -Naur language-c-0.3.3/src/Language/C/Pretty.hs language-c-0.3.3-new/src/Language/C/Pretty.hs
--- language-c-0.3.3/src/Language/C/Pretty.hs 2009-07-02 14:11:45.000000000 -0500
-+++ language-c-0.3.3-new/src/Language/C/Pretty.hs 2009-07-07 13:08:11.000000000 -0500
++++ language-c-0.3.3-new/src/Language/C/Pretty.hs 2009-12-15 09:18:04.042219887 -0600
@@ -151,7 +151,11 @@
pretty (CReturn Nothing _) = ii $ text "return" <> semi
pretty (CReturn (Just e) _) = ii $ text "return" <+> pretty e <> semi
@@ -163,17 +199,20 @@ diff -Naur language-c-0.3.3/src/Language/C/Pretty.hs language-c-0.3.3-new/src/La
let inner = text "{" $+$ mlistP ppLblDecls localLabels $+$ vcat (map pretty bis) $$ text "}"
in if p == -1 then inner else ii inner
where ppLblDecls = vcat . map (\l -> text "__label__" <+> identP l <+> semi)
-@@ -245,6 +249,7 @@
+@@ -245,6 +249,10 @@
pretty (CRestrQual _) = text "__restrict"
pretty (CInlineQual _) = text "inline"
pretty (CAttrQual a) = attrlistP [a]
+ pretty (CBlocking _) = text "__blocking"
++ pretty (CRemote _) = text "__remote"
++ pretty (CPShared _) = text "pshared"
++ pretty (CPPrivate _) = text "pprivate"
instance Pretty CStructUnion where
pretty (CStruct tag ident Nothing cattrs _) = pretty tag <+> attrlistP cattrs <+> maybeP identP ident
diff -Naur language-c-0.3.3/src/Language/C/Syntax/AST.hs language-c-0.3.3-new/src/Language/C/Syntax/AST.hs
--- language-c-0.3.3/src/Language/C/Syntax/AST.hs 2009-07-02 14:11:45.000000000 -0500
-+++ language-c-0.3.3-new/src/Language/C/Syntax/AST.hs 2009-07-07 13:08:11.000000000 -0500
++++ language-c-0.3.3-new/src/Language/C/Syntax/AST.hs 2009-12-15 09:19:46.381624818 -0600
@@ -236,6 +236,9 @@
| CBreak NodeInfo -- ^ break statement
| CReturn (Maybe CExpr)NodeInfo -- ^ return statement @CReturn returnExpr@
@@ -184,15 +223,18 @@ diff -Naur language-c-0.3.3/src/Language/C/Syntax/AST.hs language-c-0.3.3-new/sr
deriving (Data,Typeable {-! CNode !-})
-- | GNU Assembler statement
-@@ -349,6 +352,7 @@
+@@ -349,6 +352,10 @@
| CRestrQual NodeInfo
| CInlineQual NodeInfo
| CAttrQual CAttr
-+ | CBlocking NodeInfo
++ | CBlocking NodeInfo -- ^ blocking function
++ | CRemote NodeInfo -- ^ remote function
++ | CPShared NodeInfo -- ^ shared variable across pbranch blocks
++ | CPPrivate NodeInfo -- ^ private variable across pbranch blocks
deriving (Data,Typeable {-! CNode !-})
-- | C structure or union specifiers (K&R A8.3, C99 6.7.2.1)
-@@ -596,6 +600,9 @@
+@@ -596,6 +603,9 @@
nodeInfo (CBreak nodeinfo) = nodeinfo
nodeInfo (CReturn _ nodeinfo) = nodeinfo
nodeInfo (CAsm _ nodeinfo) = nodeinfo
@@ -202,11 +244,23 @@ diff -Naur language-c-0.3.3/src/Language/C/Syntax/AST.hs language-c-0.3.3-new/sr
instance Pos CStat
where posOf x = posOfNode (nodeInfo x)
-@@ -659,6 +666,7 @@
+@@ -630,6 +640,8 @@
+ nodeInfo (CExtern nodeinfo) = nodeinfo
+ nodeInfo (CTypedef nodeinfo) = nodeinfo
+ nodeInfo (CThread nodeinfo) = nodeinfo
++
++
+ instance Pos CStorageSpec
+ where posOf x = posOfNode (nodeInfo x)
+
+@@ -659,6 +671,10 @@
nodeInfo (CRestrQual nodeinfo) = nodeinfo
nodeInfo (CInlineQual nodeinfo) = nodeinfo
nodeInfo (CAttrQual d) = nodeInfo d
-+ nodeInfo (CBlocking nodeInfo) = nodeInfo
++ nodeInfo (CBlocking nodeinfo) = nodeinfo
++ nodeInfo (CRemote nodeinfo) = nodeinfo
++ nodeInfo (CPPrivate nodeinfo) = nodeinfo
++ nodeInfo (CPShared nodeinfo) = nodeinfo
instance Pos CTypeQual
where posOf x = posOfNode (nodeInfo x)
diff --git a/code/src/gsl/parser/BlockingContext.lhs b/code/src/gsl/parser/BlockingContext.lhs
index 077f394..e1bff49 100644
--- a/code/src/gsl/parser/BlockingContext.lhs
+++ b/code/src/gsl/parser/BlockingContext.lhs
@@ -271,10 +271,14 @@
> where newb = mkContextTree parent (Just next) prev b
> next:rest = fixupContextList parent (Just newb) bs
-> getPWaitDecls :: BlockingContext -> [CDecl]
-> getPWaitDecls (PWaitContext id (CPWait (CCompound _ bitems _) _) _ _ _ _ _ _) =
-> findFuncDecls bitems
-> getPWaitDecls _ = []
+> getPWaitSharedDecls :: BlockingContext -> [CDecl]
+> getPWaitSharedDecls (PWaitContext id (CPWait (CCompound _ bitems _) _) _ _ _ _ _ _) =
+> filterDecls (\_ -> True) (not . isPrivateSpec) removeSharedSpecFromDecl $ findFuncDecls bitems
+> getPWaitSharedDecls _ = []
+
+> getPWaitPrivateDecls :: BlockingContext -> [CDecl]
+> getPWaitPrivateDecls (PWaitContext id (CPWait (CCompound _ bitems _) _) _ _ _ _ _ _) =
+> filterDecls isPrivateSpec (not . isSharedSpec) removePrivateSpecFromDecl $ findFuncDecls bitems
> getPWaitId :: BlockingContext -> String
> getPWaitId (PWaitContext id _ _ _ _ _ _ _) = id
diff --git a/code/src/gsl/parser/CGen.lhs b/code/src/gsl/parser/CGen.lhs
index 3f95bab..0c33963 100644
--- a/code/src/gsl/parser/CGen.lhs
+++ b/code/src/gsl/parser/CGen.lhs
@@ -35,18 +35,18 @@ Functions to generate AST objects from C template code
> -- parse failed, so we assert fail for now. The CDecl empty constructor is needed to match types
> (Left pe) -> assert False (CDecl [] [] ni)
-> constructStmtFromC :: NodeInfo -> String -> CStat
-> constructStmtFromC ni s =
+> mkStmtFromC :: NodeInfo -> String -> CStat
+> mkStmtFromC ni s =
> let result = (execParser_ statementP (mkInputStream s) $ posOfNode ni) in
> case result of
> -- parse succeeded, so we return the statement
> (Right stmt) -> stmt
> (Left pe) -> trace ("Parse Error in:\n\n" ++
-> ("constructStmtFromC failed: " ++ s) ++
+> ("mkStmtFromC failed: " ++ s) ++
> (show pe)) $ assert False (CBreak ni)
> mkStmtsFromCLines :: NodeInfo -> String -> [CStat]
-> mkStmtsFromCLines ni lines = [constructStmtFromC ni lines]
+> mkStmtsFromCLines ni lines = [mkStmtFromC ni lines]
> mkCompoundStmt :: Maybe String -> [CStat] -> NodeInfo -> CStat
> mkCompoundStmt (Just label) stmts ni = CLabel (newIdent label ni) (CCompound [] (map CBlockStmt stmts) ni) [] ni
@@ -135,6 +135,9 @@ mkCDecl (CTypeDef "myType") [CPtrDeclr] "baz"
> genCDecl :: String -> String -> NodeInfo -> CDecl
> genCDecl typedef name ni = mkCDecl (CTypeDef (newIdent typedef ni) ni) [] name ni
+> addBlockingTQ :: CDecl -> CDecl
+> addBlockingTQ (CDecl specs inits ni) = CDecl (CTypeQual ((CBlocking ni)):specs) inits ni
+
Functions for building a struct from the name and array of members
param1Decl can be created with mkCDecl.
@@ -212,17 +215,17 @@ Make the function pointer: void (* name) (params);
> let ni = nodeInfo returnType
> in mkCDecl returnType ([mkFunDeclr params ni] ++ returnDerived) fname ni
-> mkFunDeclWithStorageSpecs :: String -> CTypeSpec -> [CDerivedDeclr] -> [CStorageSpec] -> [CDecl] -> CDecl
-> mkFunDeclWithStorageSpecs fname rType rDerived storageSpecs params =
+> mkFunDeclWithDeclSpecs :: String -> CTypeSpec -> [CDerivedDeclr] -> [CDeclSpec] -> [CDecl] -> CDecl
+> mkFunDeclWithDeclSpecs fname rType rDerived declSpecs params =
> let ni = nodeInfo rType
-> in CDecl ((map CStorageSpec storageSpecs) ++ [CTypeSpec rType])
+> in CDecl (declSpecs ++ [CTypeSpec rType])
> [(Just $ mkCDeclr fname ([mkFunDeclr params ni] ++ rDerived),
> Nothing, Nothing)] ni
-> mkFunPtrDeclWithStorageSpecs :: String -> CTypeSpec -> [CDerivedDeclr] -> [CStorageSpec] -> [CDecl] -> Maybe String -> CDecl
-> mkFunPtrDeclWithStorageSpecs fname rType rDerived storageSpecs params initName =
+> mkFunPtrDeclWithDeclSpecs :: String -> CTypeSpec -> [CDerivedDeclr] -> [CDeclSpec] -> [CDecl] -> Maybe String -> CDecl
+> mkFunPtrDeclWithDeclSpecs fname rType rDerived declSpecs params initName =
> let ni = nodeInfo rType
-> in CDecl ((map CStorageSpec storageSpecs) ++ [CTypeSpec rType])
+> in CDecl (declSpecs ++ [CTypeSpec rType])
> [(Just $ mkCDeclr fname ([CPtrDeclr [] ni, mkFunDeclr params ni] ++ rDerived),
> (if isJust initName
> then Just (CInitExpr (CVar (newIdent (fromJust initName) ni) ni) ni)
@@ -365,10 +368,10 @@ results in the statement: params->mymem = funcall(a, 123);
> let ni = nodeInfo rexpr
> in (CExpr (Just (CAssign CAssignOp (addStructPtrPrefix sname pname (CVar lvar ni)) rexpr ni)) ni)
-> mkFunDef :: CTypeSpec -> [CStorageSpec] -> String -> [CDecl] -> CStat -> CExtDecl
-> mkFunDef return sspecs fname params stmts =
+> mkFunDef :: CTypeSpec -> [CDeclSpec] -> String -> [CDecl] -> CStat -> CExtDecl
+> mkFunDef return dspecs fname params stmts =
> let ni = if null params then nodeInfo stmts else nodeInfo $ head params
-> in CFDefExt (CFunDef ((map CStorageSpec sspecs) ++ [(CTypeSpec return)])
+> in CFDefExt (CFunDef (dspecs ++ [(CTypeSpec return)])
> (CDeclr (Just $ newIdent fname ni)
> [(CFunDeclr (Right (params, False)) [] ni)]
> Nothing [] ni)
@@ -411,3 +414,15 @@ results in the statement: params->mymem = funcall(a, 123);
> mkLabel :: String -> [CStat] -> NodeInfo -> CStat
> mkLabel s stmts ni = (CLabel (newIdent s ni) (CCompound [] (map CBlockStmt stmts) ni) [] ni)
+> canonCDecl :: CDecl -> String
+> canonCDecl (CDecl declspecs derived _) =
+> let t = getTypeSpec declspecs
+> tstr = case t of
+> (CSUType (CStruct CStructTag (Just n) _ _ _) _) -> "struct_" ++ (identToString n)
+> (CTypeDef n _) -> identToString n
+> (CSUType (CStruct CUnionTag (Just n) _ _ _) _) -> "union_" ++ (identToString n)
+> (CEnumType (CEnum (Just n) _ _ _) _) -> "enum_" ++ (identToString n)
+> _ -> show $ pretty t
+> ptrs = filter isDerivedPtr (join $ map getDerivedDeclrs derived)
+> ptrStr = concat [ "_ptr" | p <- ptrs ]
+> in tstr ++ ptrStr
diff --git a/code/src/gsl/parser/CParse.lhs b/code/src/gsl/parser/CParse.lhs
index 9ac56a6..de068d5 100644
--- a/code/src/gsl/parser/CParse.lhs
+++ b/code/src/gsl/parser/CParse.lhs
@@ -69,6 +69,10 @@ Will result in ["a", "b", "c"]
> isTypeDefSpec (CStorageSpec (CTypedef _)) = True
> isTypeDefSpec _ = False
+> isTypeDefTypeSpec :: CDeclSpec -> Bool
+> isTypeDefTypeSpec (CTypeSpec (CTypeDef _ _)) = True
+> isTypeDefTypeSpec _ = False
+
> isVoidTypeSpec :: CDeclSpec -> Bool
> isVoidTypeSpec (CTypeSpec (CVoidType _)) = True
> isVoidTypeSpec _ = False
@@ -77,7 +81,8 @@ Will result in ["a", "b", "c"]
> isStructDecl (CDecl specs initdecls ni) = any isStructTypeSpec specs
> isTypeDefDecl :: CDecl -> Bool
-> isTypeDefDecl (CDecl specs initdecls ni) = any isTypeDefSpec specs
+> isTypeDefDecl (CDecl (s:specs) initdecls ni) = isTypeDefSpec s
+> isTypeDefDecl _ = False
> structSpecHasName :: CDeclSpec -> Bool
> structSpecHasName (CTypeSpec (CSUType (CStruct _ (Just _) _ _ _) _)) = True
@@ -97,13 +102,28 @@ Will result in ["a", "b", "c"]
> isTypeDefSpec s1 && isStructTypeSpec s2 && structSpecHasFields s2
> isTypeDefOfInlineStruct _ = False
+> isTypeDefOfTypeDef :: CDecl -> Bool
+> isTypeDefOfTypeDef (CDecl (s1:s2:[]) _ _) =
+> isTypeDefSpec s1 && isTypeDefTypeSpec s2
+> isTypeDefOfTypeDef _ = False
+
+> getStructName :: CDeclSpec -> Maybe String
+> getStructName (CTypeSpec (CSUType (CStruct _ n _ _ _) _)) = if isJust n then Just $ identToString $ fromJust n else Nothing
+> getStructName _ = Nothing
+
> getStructTypeDefInfo :: CDecl -> Maybe (Maybe String, String)
> getStructTypeDefInfo d@(CDecl (s1:s2:[]) initdecls ni)
> | isTypeDefSpec s1 && isStructTypeSpec s2 =
-> let (CTypeSpec (CSUType (CStruct _ n _ _ _) _)) = s2
-> sname = if isJust n then Just $ identToString $ fromJust n else Nothing
+> let ((Just (CDeclr (Just (Ident tname _ _)) _ _ _ _)), _, _) = head initdecls
+> in Just (getStructName s2, tname)
+> | otherwise = Nothing
+
+> getTypeDefTypeDefInfo :: CDecl -> Maybe (String, String)
+> getTypeDefTypeDefInfo d@(CDecl (s1:s2:[]) initdecls ni)
+> | isTypeDefSpec s1 && isTypeDefTypeSpec s2 =
+> let (CTypeSpec (CTypeDef (Ident pname _ _) _)) = s2
> ((Just (CDeclr (Just (Ident tname _ _)) _ _ _ _)), _, _) = head initdecls
-> in Just (sname, tname)
+> in Just (pname, tname)
> | otherwise = Nothing
> getStructInfo :: CDecl -> Maybe (Maybe String, [CDecl])
@@ -124,6 +144,10 @@ Will result in ["a", "b", "c"]
> isVarDecl d@(CDecl specs initdecls ni) =
> (not $ isFunDecl d) && (not $ any isTypeDefSpec specs) && hasDeclrName d
+> getVarName :: CDecl -> String
+> getVarName d@(CDecl _ initdecls _) = vname
+> where ((Just (CDeclr (Just (Ident vname _ _)) _ _ _ _)), _, _) = head initdecls
+
For a compound block item (part of a compound block of statements), is the item a declaration?
> isFuncDecl :: CBlockItem -> Bool
@@ -228,16 +252,79 @@ Get the return type and derived declarators for a function definition
> isBlockingSpec (CTypeQual (CBlocking _)) = True
> isBlockingSpec _ = False
+> isPrivateSpec :: CDeclSpec -> Bool
+> isPrivateSpec (CTypeQual (CPPrivate _)) = True
+> isPrivateSpec _ = False
+
+> isSharedSpec :: CDeclSpec -> Bool
+> isSharedSpec (CTypeQual (CPShared _)) = True
+> isSharedSpec _ = False
+
+> isStdSpec :: CDeclSpec -> Bool
+> isStdSpec c = (not $ isBlockingSpec c) && (not $ isPrivateSpec c) && (not $ isSharedSpec c)
+
+> isRemoteSpec :: CDeclSpec -> Bool
+> isRemoteSpec (CTypeQual (CRemote _)) = True
+> isRemoteSpec _ = False
+
+> getDeclSpecs :: CFunDef -> [CDeclSpec]
+> getDeclSpecs (CFunDef declspecs _ _ _ _) = declspecs
+
+> getAllStorageSpecs :: [CDeclSpec] -> [CStorageSpec]
+> getAllStorageSpecs declspecs = map getSto $ filter isSto declspecs
+> where isSto (CStorageSpec s) = True
+> isSto _ = False
+> getSto (CStorageSpec s) = s
+
> getStorageSpecs :: CFunDef -> [CStorageSpec]
> getStorageSpecs (CFunDef declspecs _ _ _ _) = getStorageSpecsFromDeclSpecs declspecs
> getStorageSpecsFromDeclSpecs :: [CDeclSpec] -> [CStorageSpec]
> getStorageSpecsFromDeclSpecs ((CStorageSpec s):specs)
-> | not $ isBlockingSpec (CStorageSpec s) = s:(getStorageSpecsFromDeclSpecs specs)
+> | isStdSpec (CStorageSpec s) = s:(getStorageSpecsFromDeclSpecs specs)
> | otherwise = getStorageSpecsFromDeclSpecs specs
> getStorageSpecsFromDeclSpecs (s:specs) = getStorageSpecsFromDeclSpecs specs
> getStorageSpecsFromDeclSpecs [] = []
+> filterDecls :: (CDeclSpec -> Bool) -> (CDeclSpec -> Bool) -> (CDecl -> CDecl) -> [CDecl] -> [CDecl]
+> filterDecls anyFunc allFunc transFunc decls = map transFunc $ filter isFilterDecl decls
+> where isFilterDecl (CDecl specs l ni) = any anyFunc specs && all allFunc specs
+
+> isStorageSpec :: CDeclSpec -> Bool
+> isStorageSpec (CStorageSpec _) = True
+> isStorageSpec _ = False
+
+> isTypeQual :: CDeclSpec -> Bool
+> isTypeQual (CTypeQual _) = True
+> isTypeQual _ = False
+
+> isStdTypeQual :: CDeclSpec -> Bool
+> isStdTypeQual (CTypeQual (CRemote _)) = False
+> isStdTypeQual (CTypeQual (CBlocking _)) = False
+> isStdTypeQual (CTypeQual (CPPrivate _)) = False
+> isStdTypeQual (CTypeQual (CPShared _)) = False
+> isStdTypeQual (CTypeQual _) = True
+> isStdTypeQual _ = False
+
+> filterStdDeclSpecs :: [CDeclSpec] -> [CDeclSpec]
+> filterStdDeclSpecs declspecs = filter (\s -> isStorageSpec s || isStdTypeQual s) declspecs
+
+> getStdDeclSpecs :: CFunDef -> [CDeclSpec]
+> getStdDeclSpecs (CFunDef declspecs _ _ _ _) = filterStdDeclSpecs declspecs
+
+> removeSharedSpecFromDecl :: CDecl -> CDecl
+> removeSharedSpecFromDecl (CDecl specs l ni) = (CDecl rspecs l ni)
+> where rspecs = filter (not . isSharedSpec) specs
+
+> removePrivateSpecFromDecl :: CDecl -> CDecl
+> removePrivateSpecFromDecl (CDecl specs l ni) = (CDecl rspecs l ni)
+> where rspecs = filter (not . isPrivateSpec) specs
+
+> removeRemoteSpecFromFunDef :: CExtDecl -> CExtDecl
+> removeRemoteSpecFromFunDef (CFDefExt (CFunDef specs declr decls stmt ni)) =
+> let newspecs = filter (not . isRemoteSpec) specs
+> in (CFDefExt (CFunDef newspecs declr decls stmt ni))
+
Get the local declarations for a function definition
> getFunLocalDeclarations :: CFunDef -> [CDecl]
diff --git a/code/src/gsl/parser/gs-parser.lhs b/code/src/gsl/parser/gs-blocking-parser.lhs
similarity index 90%
rename from code/src/gsl/parser/gs-parser.lhs
rename to code/src/gsl/parser/gs-blocking-parser.lhs
index 4be7f2a..166a9e3 100644
--- a/code/src/gsl/parser/gs-parser.lhs
+++ b/code/src/gsl/parser/gs-blocking-parser.lhs
@@ -1,4 +1,4 @@
-> module Main where
+> module BlockingParser where
> import Language.C
> import Language.C.Data.Position
> import Language.C.System.GCC -- preprocessor used
@@ -30,12 +30,12 @@
> import Header
> mkErrorCBPostHandler :: String -> ReturnType -> String -> NodeInfo -> CStat
-> mkErrorCBPostHandler fname retType ctlName ni = constructStmtFromC ni $
+> mkErrorCBPostHandler fname retType ctlName ni = mkStmtFromC ni $
> "if (!(__gs_postret == GS_POSTED || __gs_postret == GS_COMPLETE))" ++
> "{ fprintf(stderr, \"INVALID POST RETURN: %s:%d: post call did not return GS_POSTED or GS_COMPLETE\\n\", \"" ++ fname ++ "\", " ++ (show $ posRow $ posOfNode ni) ++ "); exit(1); }"
> mkErrorPostHandler :: String -> ReturnType -> String -> NodeInfo -> CStat
-> mkErrorPostHandler fname retType ctlName ni = constructStmtFromC ni $
+> mkErrorPostHandler fname retType ctlName ni = mkStmtFromC ni $
> "if (!(__gs_postret == GS_POSTED || __gs_postret == GS_COMPLETE))" ++
> "{ fprintf(stderr, \"INVALID POST RETURN: %s:%d: post call did not return GS_POSTED or GS_COMPLETE\\n\", \"" ++ fname ++ "\", " ++ (show $ posRow $ posOfNode ni) ++ "); exit(1); }"
@@ -43,10 +43,10 @@
> mkPBreakStmts :: String -> String -> NodeInfo -> ([CDecl], [CStat])
> mkPBreakStmts prefix funName ni =
> ([mkCDecl (CIntType ni) [] "__gs_cancel_ret" ni],
-> [constructStmtFromC ni $ "done_ctl->parent->hit_pbreak = 1;",
-> constructStmtFromC ni $ "gs_list_del(&done_ctl->link);",
-> constructStmtFromC ni $ "__gs_cancel_ret = gs_cancel_children(done_ctl->context, done_ctl->parent);",
-> constructStmtFromC ni $
+> [mkStmtFromC ni $ "done_ctl->parent->hit_pbreak = 1;",
+> mkStmtFromC ni $ "gs_list_del(&done_ctl->link);",
+> mkStmtFromC ni $ "__gs_cancel_ret = gs_cancel_children(done_ctl->context, done_ctl->parent);",
+> mkStmtFromC ni $
> "if (__gs_cancel_ret != 0)" ++
> "{ fprintf(stderr, \"INVALID CANCEL RETURN: %s:%d: cancel did not return 0\\n\", \"" ++ funName ++ "\", " ++ (show $ posRow $ posOfNode ni) ++ "); exit(1); }"])
@@ -57,14 +57,14 @@ either from a pbreak, or from an external cancel call of the entire blocking fun
> mkPBranchCallbackStartStmts prefix funName ni =
> ([mkCDecl (CIntType ni) [] "__gs_pwait_done" ni,
> mkStructPtrDecl (mkStructCtlName $ funName) "done_ctl" ni],
-> [constructStmtFromC ni $ "done_ctl = "++prefix++";",
-> constructStmtFromC ni $ "gs_mutex_lock(&done_ctl->parent->mutex);"])
+> [mkStmtFromC ni $ "done_ctl = "++prefix++";",
+> mkStmtFromC ni $ "gs_mutex_lock(&done_ctl->parent->mutex);"])
> mkPBranchDeleteStmts :: NodeInfo -> [CStat]
-> mkPBranchDeleteStmts ni = [constructStmtFromC ni $ "gs_list_del(&done_ctl->link);"]
+> mkPBranchDeleteStmts ni = [mkStmtFromC ni $ "gs_list_del(&done_ctl->link);"]
> mkPBranchDoneStmts :: String -> String -> NodeInfo -> [CStat]
-> mkPBranchDoneStmts prefix funName ni = map (constructStmtFromC ni)
+> mkPBranchDoneStmts prefix funName ni = map (mkStmtFromC ni)
> ["done_ctl->parent->completed++;",
> "__gs_pwait_done = done_ctl->parent->allposted == 1 && \
> \ done_ctl->parent->posted == done_ctl->parent->completed;",
@@ -72,21 +72,21 @@ either from a pbreak, or from an external cancel call of the entire blocking fun
> "free(done_ctl);"]
> mkPBranchCBDoneStmts :: BlockingContext -> NodeInfo -> [CStat]
-> mkPBranchCBDoneStmts pb ni = map (constructStmtFromC ni)
+> mkPBranchCBDoneStmts pb ni = map (mkStmtFromC ni)
> ["if(!__gs_pwait_done) goto __gs_callback_end;"]
> mkPBranchPostDoneStmts :: BlockingContext -> NodeInfo -> [CStat]
-> mkPBranchPostDoneStmts pb ni = map (constructStmtFromC ni)
+> mkPBranchPostDoneStmts pb ni = map (mkStmtFromC ni)
> ["if(!__gs_pwait_done) goto __gs_" ++ (getPBranchId pb) ++ "_end;"]
> mkDoneStmts :: NodeInfo -> [CStat]
> mkDoneStmts ni = [mkGoto "__gs_callback_end" ni]
> mkDoneCtlSetStmt :: String -> NodeInfo -> CStat
-> mkDoneCtlSetStmt p ni = constructStmtFromC ni $ p++" = done_ctl->parent;"
+> mkDoneCtlSetStmt p ni = mkStmtFromC ni $ p++" = done_ctl->parent;"
-> mkPWaitInitStmts :: String -> NodeInfo -> [CStat]
-> mkPWaitInitStmts prefix ni = mkStmtsFromCLines ni $
+> mkPWaitInitStmts :: String -> String -> NodeInfo -> [CStat]
+> mkPWaitInitStmts pwaitParams prefix ni = mkStmtsFromCLines ni $
> "{ \
> \ "++prefix++"->posted = 0; \
> \ "++prefix++"->completed = 0; \
@@ -97,15 +97,16 @@ either from a pbreak, or from an external cancel call of the entire blocking fun
> \ "++prefix++"->children.next = &("++prefix++"->children); \
> \ "++prefix++"->children.prev = &("++prefix++"->children); \
> \ "++prefix++"->in_pwait = 1; \
+> \ "++prefix++"->"++pwaitParams++".shared_params = &"++prefix++"->"++pwaitParams++".shared; \
> \}"
> mkPWaitFinishStmts :: [CStat] -> String -> NodeInfo -> [CStat]
> mkPWaitFinishStmts afterPWaitStmts prefix ni = [mkCompoundWithDecls Nothing
> [mkCDecl (CIntType ni) [] "__gs_pwait_done" ni]
-> [constructStmtFromC ni $ "gs_mutex_lock(&"++prefix++"->mutex);",
-> constructStmtFromC ni $ "__gs_pwait_done = "++prefix++"->posted == "++prefix++"->completed;",
-> constructStmtFromC ni $ prefix++"->allposted = 1;",
-> constructStmtFromC ni $ "gs_mutex_unlock(&"++prefix++"->mutex);",
+> [mkStmtFromC ni $ "gs_mutex_lock(&"++prefix++"->mutex);",
+> mkStmtFromC ni $ "__gs_pwait_done = "++prefix++"->posted == "++prefix++"->completed;",
+> mkStmtFromC ni $ prefix++"->allposted = 1;",
+> mkStmtFromC ni $ "gs_mutex_unlock(&"++prefix++"->mutex);",
> mkIfElseStmt (Just (constructExprFromC ni "__gs_pwait_done"))
> afterPWaitStmts []] ni]
@@ -128,16 +129,17 @@ either from a pbreak, or from an external cancel call of the entire blocking fun
> mkPBranchPostStmts pwaitName prefix parentPrefix fname stmts ni =
> [mkCompoundWithDecls Nothing
> [constructDeclFromC ni ("struct " ++ (mkStructCtlName fname) ++ " *" ++ prefix ++ ";")]
-> ([constructStmtFromC ni $ prefix ++ " = malloc(sizeof(*" ++ prefix ++ "));",
-> constructStmtFromC ni $ prefix ++ "->parent = " ++ parentPrefix ++ ";",
-> constructStmtFromC ni $ prefix++"->context = "++parentPrefix++"->context;",
-> constructStmtFromC ni $ prefix++"->hints = "++parentPrefix++"->hints;",
-> constructStmtFromC ni $ prefix++"->params = "++parentPrefix++"->params;",
-> constructStmtFromC ni $ "memcpy(&"++prefix++"->"++pwaitName++",&"++parentPrefix++"->"++pwaitName++", sizeof("++prefix++"->"++pwaitName++"));",
-> constructStmtFromC ni $ "gs_mutex_lock(&("++prefix++"->parent->mutex));",
-> constructStmtFromC ni $ "("++prefix++"->parent->posted)++;",
-> constructStmtFromC ni $ "gs_list_add(&"++prefix++"->link, &"++prefix++"->parent->children);",
-> constructStmtFromC ni $ "gs_mutex_unlock(&("++prefix++"->parent->mutex));"]
+> ([mkStmtFromC ni $ prefix ++ " = malloc(sizeof(*" ++ prefix ++ "));",
+> mkStmtFromC ni $ prefix ++ "->parent = " ++ parentPrefix ++ ";",
+> mkStmtFromC ni $ prefix++"->context = "++parentPrefix++"->context;",
+> mkStmtFromC ni $ prefix++"->hints = "++parentPrefix++"->hints;",
+> mkStmtFromC ni $ prefix++"->params = "++parentPrefix++"->params;",
+> mkStmtFromC ni $ "memcpy(&"++prefix++"->"++pwaitName++".private,&"++parentPrefix++"->"++pwaitName++".private, sizeof("++prefix++"->"++pwaitName++".private));",
+> mkStmtFromC ni $ prefix++"->"++pwaitName++".shared_params = &"++parentPrefix++"->"++pwaitName++".shared;",
+> mkStmtFromC ni $ "gs_mutex_lock(&("++prefix++"->parent->mutex));",
+> mkStmtFromC ni $ "("++prefix++"->parent->posted)++;",
+> mkStmtFromC ni $ "gs_list_add(&"++prefix++"->link, &"++prefix++"->parent->children);",
+> mkStmtFromC ni $ "gs_mutex_unlock(&("++prefix++"->parent->mutex));"]
> ++ stmts) ni]
> mkBlockingParamsParallelFields :: String -> Bool -> NodeInfo -> [CDecl]
@@ -226,14 +228,21 @@ either from a pbreak, or from an external cancel call of the entire blocking fun
> (fromJust $ getTypeName i)
> mapM_ lookupAndReg (filter isStructDecl notBlockingFields)
-> registerTypedef :: CDecl -> Maybe String -> WalkerT ()
-> registerTypedef d altSname = do
+> registerTypedefStruct :: CDecl -> Maybe String -> WalkerT ()
+> registerTypedefStruct d altSname = do
> let t = getStructTypeDefInfo d
> (Just (sn, tname)) = t
> sname = if isJust sn then sn else altSname
> assert (isJust t && isJust sname) return ()
> lookupAndRegisterBlockingTypedef (fromJust sname) tname
+> registerTypedefTypedef :: CDecl -> WalkerT ()
+> registerTypedefTypedef d = do
+> let t = getTypeDefTypeDefInfo d
+> (Just (pn, tname)) = t
+> assert (isJust t) return ()
+> lookupAndRegisterBlockingTypedef pn tname
+
> registerBlockingDecl :: Bool -> CExtDecl -> WalkerT [CExtDecl]
> registerBlockingDecl ph e@(CDeclExt d@(CDecl specifiers initdecls ni))
@@ -243,17 +252,23 @@ either from a pbreak, or from an external cancel call of the entire blocking fun
> (show $ posRow $ posOfNode $ nodeInfo d) ++ "_" ++
> (show $ posColumn $ posOfNode $ nodeInfo d)
> registerStruct d (Just name)
-> registerTypedef d (Just name)
+> registerTypedefStruct d (Just name)
> if ph then
> return [e]
> else return []
> | isTypeDefOfPredefStruct d = do
-> registerTypedef d Nothing
+> registerTypedefStruct d Nothing
> if ph then
> return [e]
> else return []
+> | isTypeDefOfTypeDef d = do
+> registerTypedefTypedef d
+> if ph then
+> return [e]
+> else return []
+
Register structs containing blocking function pointers as fields: struct a { __blocking int (*myfun) (); }
Or fields that are structs with blocking function pointers: struct b { struct a mya; }
etc. etc.
@@ -476,8 +491,29 @@ From a blocking function definition, Construct an external declaration parameter
> mkStructPBranchName :: String -> String -> String -> String
> mkStructPBranchName name pwaitName id = pwaitName ++ "_" ++ name ++ "_" ++ id ++ "_params"
-> mkParamPWaitName :: String -> String
-> mkParamPWaitName id = id ++ "_params"
+> mkPrivateParamPWaitName :: String -> String -> String
+> mkPrivateParamPWaitName name id = name ++ "_" ++ id ++ "_private_params"
+
+> mkSharedParamPWaitName :: String -> String -> String
+> mkSharedParamPWaitName name id = name ++ "_" ++ id ++ "_shared_params"
+
+> mkPWaitName :: String -> String
+> mkPWaitName id = id ++ "_params"
+
+> mkPrivateName :: String
+> mkPrivateName = "private"
+
+> mkPrivatePWaitName :: String -> String
+> mkPrivatePWaitName id = (mkPWaitName id) ++ "." ++ mkPrivateName
+
+> mkSharedName :: String
+> mkSharedName = "shared"
+
+> mkSharedPtrName :: String
+> mkSharedPtrName = "shared_params"
+
+> mkSharedPWaitName :: String -> String
+> mkSharedPWaitName id = (mkPWaitName id) ++ "." ++ mkSharedPtrName
> mkParamPBranchName :: String -> String
> mkParamPBranchName id = id ++ "_params"
@@ -500,9 +536,9 @@ From a blocking function definition, Construct an external declaration parameter
> removeInits :: (String, [CDecl]) -> (String, [CDecl])
> removeInits (pwaitName, pwaitDecls) = (pwaitName, (map removeInitFromDecl pwaitDecls))
-> mkPWaitExtDecl :: String -> (String, [CDecl]) -> NodeInfo -> CExtDecl
-> mkPWaitExtDecl fname (pwaitName, pwaitDecls) ni =
-> genStructExtDecl (mkStructPWaitName fname pwaitName) pwaitDecls ni
+> mkPWaitExtDecl :: (String -> String) -> (String, [CDecl]) -> NodeInfo -> CExtDecl
+> mkPWaitExtDecl snamef (pwaitName, pwaitDecls) ni =
+> genStructExtDecl (snamef pwaitName) pwaitDecls ni
> mkBlockingPBranchStructs :: CFunDef -> (String, BlockingContext) -> WalkerT [CExtDecl]
> mkBlockingPBranchStructs funDef (pwaitName, pwaitCtx) = do
@@ -529,13 +565,21 @@ From a blocking function definition, Construct an external declaration parameter
> let fname = getFunDefName funDef
> ni = nodeInfo funDef
> pwaits = getPWaits bctx
-> pwaitDecls = zip (map getPWaitId pwaits) (map getPWaitDecls pwaits)
-> params = map removeInits pwaitDecls
-> allParams = zipWith (addPBranchParams funDef) pwaits params
-> pwaitStructs = map (\p -> mkPWaitExtDecl fname p ni) allParams
+> ids = map getPWaitId pwaits
+> privatePWaitDecls = zip ids (map getPWaitPrivateDecls pwaits) -- :: [(pwait_id, [private_decl])]
+> sharedPWaitDecls = zip ids (map getPWaitSharedDecls pwaits) -- :: [(pwait_id, [shared_decl])]
+> private = map removeInits privatePWaitDecls -- :: [(pwait_id, [private_decl_no_inits])]
+> shared = map removeInits sharedPWaitDecls -- :: [(pwait_id, [shared_decl_no_inits])]
+> sharedWithPBranch = zipWith (addPBranchParams funDef) pwaits shared -- :: [(pwait_id, [shared_decl_no_inits] ++ [pbranch_struct_decl])]
+> privatePWaitStructs = map (\p -> mkPWaitExtDecl (mkPrivateParamPWaitName fname) p ni) private
+> sharedPWaitStructs = map (\p -> mkPWaitExtDecl (mkSharedParamPWaitName fname) p ni) sharedWithPBranch
+> pwaitParams = map (\id -> (id, [mkStructDecl (mkPrivateParamPWaitName fname id) mkPrivateName ni,
+> mkStructDecl (mkSharedParamPWaitName fname id) mkSharedName ni,
+> mkStructPtrDecl (mkSharedParamPWaitName fname id) mkSharedPtrName ni])) ids -- [(pwait_id, [private_struct, shared_struct])]
+> pwaitStructs = map (\p -> mkPWaitExtDecl (mkStructPWaitName fname) p ni) pwaitParams
> pwaitNamePairs = zip (map getPWaitId pwaits) pwaits
> pbranchStructs <- liftM concat $ mapM (mkBlockingPBranchStructs funDef) pwaitNamePairs
-> return $ pbranchStructs ++ pwaitStructs
+> return $ pbranchStructs ++ privatePWaitStructs ++ sharedPWaitStructs ++ pwaitStructs
> | otherwise = return []
> mkPBranchExtDecl :: String -> String -> (String, [CDecl]) -> NodeInfo -> CExtDecl
@@ -556,7 +600,7 @@ From a blocking function definition, Construct an external declaration parameter
> fieldsDecl = mkStructDecl spName "fields" ni
> paramsDecl = mkStructPtrDecl spName "params" ni
> pwaitDecls = map (\p -> mkStructDecl (mkStructPWaitName fname (getPWaitId p))
-> (mkParamPWaitName (getPWaitId p)) ni)
+> (mkPWaitName (getPWaitId p)) ni)
> $ getPWaits bctx
> return $ genStructExtDecl ctlName
> (bparams ++ pparams ++
@@ -626,7 +670,7 @@ runfun(ctl->fields.a, ctl->fields.b, ctl->fields.c, ctl->fields.d);
> pwaitCtx = getPWaitAncestor bctx
> locals = join $ map getCDeclNames $ getPBranchDecls pbranchCtx
> in (addParams2Prefixes ctlPrefix
-> (mkParamPWaitName (getPWaitId pwaitCtx))
+> (mkPWaitName (getPWaitId pwaitCtx))
> (mkParamPBranchName (getPBranchId pbranchCtx))
> locals) stmt
> | otherwise = stmt
@@ -635,10 +679,11 @@ runfun(ctl->fields.a, ctl->fields.b, ctl->fields.c, ctl->fields.d);
> trPWaitLocals ctlPrefix bctx stmt
> | hasPWaitAncestor bctx =
> let pwaitCtx = getPWaitAncestor bctx
-> locals = join $ map getCDeclNames $ getPWaitDecls pwaitCtx
-> in (addParamsPrefixes ctlPrefix
-> (mkParamPWaitName (getPWaitId pwaitCtx))
-> locals) stmt
+> privateLocals = join $ map getCDeclNames $ getPWaitPrivateDecls pwaitCtx
+> sharedLocals = join $ map getCDeclNames $ getPWaitSharedDecls pwaitCtx
+> privatePrefixedStmt = addParamsPrefixes ctlPrefix (mkPrivatePWaitName (getPWaitId pwaitCtx)) privateLocals stmt
+> allPrefixedStmt = addParamsPtrPrefixes ctlPrefix (mkSharedPWaitName (getPWaitId pwaitCtx)) sharedLocals privatePrefixedStmt
+> in allPrefixedStmt
> | otherwise = stmt
> trFunLocals :: String -> BlockingContext -> CStat -> CStat
@@ -670,8 +715,8 @@ to calling the appropriate callback
> in mkCompoundStmt Nothing [CExpr (Just (CCall (CMember (mkVar "ctl" ni)
> (newIdent "callback" ni) True ni)
> ([constructExprFromC ni "ctl->user_ptr"] ++ retparam) ni)) ni,
-> constructStmtFromC ni "free(ctl);",
-> constructStmtFromC ni "return;"] ni
+> mkStmtFromC ni "free(ctl);",
+> mkStmtFromC ni "return;"] ni
> swapReturnWithCallback c = c
@@ -686,8 +731,8 @@ to calling the appropriate callback
> [(CExpr (Just (CCall (CMember (mkVar "ctl" ni)
> (newIdent "callback" ni) True ni)
> ([constructExprFromC ni "ctl->user_ptr"] ++ retparam) ni)) ni),
-> constructStmtFromC ni "free(ctl);",
-> constructStmtFromC ni "return 0;"] ni
+> mkStmtFromC ni "free(ctl);",
+> mkStmtFromC ni "return 0;"] ni
> swapPostReturnWithCallback c = c
> transformPostFuncReturnStmts :: CStat -> CStat
@@ -744,7 +789,7 @@ params->val = val;
> setPBDone mkPBranchPostDoneStmts
> setTransExit transformPostFuncReturnStmts
> gspWarn
-> ("The blocking function: " ++ fname ++ " does not contain any blocking statements\n")
+> ("The blocking function '" ++ fname ++ "' does not contain any blocking statements\n")
> (getNI b)
> return tlInitStmts
@@ -921,28 +966,32 @@ Special case where the if has blocking call(s), but the else doesn't (an else ma
> getParallelStmts pb@(PBranchContext _ branchDef (b:branchStmts) _ _ _ _ _) tr = do
> pp <- getPrefix
> let ni = getNI pb
+> nbStmtsBeforePB = nbStmtsBefore pb
> nbStmts = nbStmtsBefore b
> pbDeclInits = getInitsFromDecls $ getLocalDeclarations branchDef
> ctxInitStmts = getCtxInitStmts b
-> pwaitName = mkParamPWaitName $ getPWaitId $ getPWaitAncestor pb
+> pwaitName = mkPWaitName (getPWaitId $ getPWaitAncestor pb)
> pbend = [mkLabel ("__gs_" ++ (getPBranchId pb) ++ "_end") [] ni]
-> initStmts <- translateForCB b $ (pbDeclInits ++ nbStmts ++ ctxInitStmts)
> afterPBranchNBStmts <- translateForCB pb (nbStmtsAfter pb)
> pushPrefix "child_ctl"
+> initStmts <- translateForCB b $ (pbDeclInits ++ nbStmts ++ ctxInitStmts)
+> setPBDone mkPBranchPostDoneStmts
> branchPostStmts <- generatePostStmts (Just b) []
> cp <- getPrefix
-> let branchStmts = mkPBranchPostStmts pwaitName cp pp (getParentName pb) branchPostStmts (nodeInfo branchDef)
+> let branchStmts = mkPBranchPostStmts pwaitName cp pp (getParentName pb) (initStmts ++ branchPostStmts) (nodeInfo branchDef)
> popPrefix
-> return $ initStmts ++ branchStmts ++ pbend ++ afterPBranchNBStmts
+> return $ branchStmts ++ pbend ++ afterPBranchNBStmts
> getParallelStmts pw@(PWaitContext _ waitDef waitStmts@(w:ws) before after parent next prev) tr = do
> let nbStmts = nbStmtsBefore w
> pwaitDeclInits = getInitsFromDecls $ getLocalDeclarations waitDef
+> pwParamsName = mkPWaitName (getPWaitId pw)
> firstStmts <- translateForCB w (pwaitDeclInits ++ nbStmts)
> pStmts <- liftM concat $ mapM (\b -> (getParallelStmts b tr)) waitStmts
> p <- getPrefix
> afterPWaitStmts <- generateAfterStmts pw tr
-> return $ (mkPWaitInitStmts p $ getNI pw) ++ firstStmts ++ pStmts ++ (mkPWaitFinishStmts afterPWaitStmts p $ getNI pw)
+> return $ (mkPWaitInitStmts pwParamsName p $ getNI pw) ++
+> firstStmts ++ pStmts ++ (mkPWaitFinishStmts afterPWaitStmts p $ getNI pw)
> getParallelStmts b@(ForContext forDef forStmts@(f:fs) nbBefore nbAfter parent next prev) tr = do
> p <- getPrefix
@@ -1169,7 +1218,7 @@ and finally the code up-to the first blocking call.
> -- statements before first blocking call
> ++ (map (trLocals prefix bctx) blockingStmts)
> ++ [mkLabel "__gs_post_end" [] $ getNI bctx,
-> constructStmtFromC (getNI bctx) "if(op_id) *op_id = gs_id_gen(0, (unsigned long)ctl);",
+> mkStmtFromC (getNI bctx) "if(op_id) *op_id = gs_id_gen(0, (unsigned long)ctl);",
> CReturn (Just (mkVar "__gs_postret" $ getNI bctx)) $ getNI bctx]) $ getNI bctx
> mkCBParam :: (CTypeSpec, [CDerivedDeclr]) -> NodeInfo -> [CDecl]
@@ -1195,21 +1244,21 @@ and finally the code up-to the first blocking call.
> mkPostDecl f@((,,) fname return params) declspecs =
> let ni = nodeInfo $ fst return
> fparams = mkPostParams f
-> in mkFunDeclWithStorageSpecs
+> in mkFunDeclWithDeclSpecs
> (fname ++ "_post")
> (CTypeDef (newIdent "gs_ret_t" ni) ni) []
-> (getStorageSpecsFromDeclSpecs declspecs)
+> (filterStdDeclSpecs declspecs)
> fparams
> mkPostPtrDecl :: Bool -> (String, (CTypeSpec, [CDerivedDeclr]), [CDecl]) -> [CDeclSpec] -> CDecl
> mkPostPtrDecl extern f@((,,) fname return params) declspecs =
> let ni = nodeInfo $ fst return
> fparams = mkPostParams f
-> in mkFunPtrDeclWithStorageSpecs
+> in mkFunPtrDeclWithDeclSpecs
> fname
> (CTypeDef (newIdent "gs_ret_t" ni) ni) []
-> ((getStorageSpecsFromDeclSpecs declspecs) ++
-> (if extern then [CExtern ni] else []))
+> ((filterStdDeclSpecs declspecs) ++
+> (if extern then [CStorageSpec $ CExtern ni] else []))
> fparams
> (if not extern then Just (fname ++ "_post") else Nothing)
@@ -1219,7 +1268,7 @@ and finally the code up-to the first blocking call.
> params = map translateBlockingFunParam $ removeVoid decls
> ni = getNI bctx
> in mkFunDef (CTypeDef (newIdent "gs_ret_t" ni) ni) -- return type
-> (getStorageSpecs funDef) -- get the storage specifiers for the function
+> (getStdDeclSpecs funDef) -- get the storage specifiers for the function
> (mkPostFunName "params" $ getFunDefName funDef) -- function name
> (params ++ (mkBlockingParamsForPost funDef))
> (mkPostStmts prefix bctx funDef postStmts) -- statements
diff --git a/code/src/gsl/parser/gs-remote-parser.lhs b/code/src/gsl/parser/gs-remote-parser.lhs
new file mode 100644
index 0000000..9c4c991
--- /dev/null
+++ b/code/src/gsl/parser/gs-remote-parser.lhs
@@ -0,0 +1,518 @@
+> module RemoteParser where
+> import Language.C
+> import Language.C.Data.Position
+> import Language.C.System.GCC -- preprocessor used
+> import Language.C.Data.Ident
+> import System.Environment
+> import System.Console.GetOpt
+> import System.Exit
+> import Data.Typeable
+> import Data.Maybe
+> import Data.Either
+> import Data.HashTable
+> import Data.Generics
+> import Data.Generics.Schemes
+> import qualified Data.ByteString
+> import qualified Data.ByteString.Char8
+> import Control.Monad.State
+> import Control.Exception
+> import Data.List
+> import CGen
+> import CParse
+> import CUtils
+> import System.IO.Unsafe
+> import Debug.Trace
+> import Data.Tree
+> import Serialize
+> import CParse
+> import CGen
+> import Header
+
+> type RemoteTypeRegistry = [String]
+
+> data Remote = Remote {
+> filename :: String,
+> typeReg :: RemoteTypeRegistry
+> }
+
+> newRemoteState :: String -> IO Remote
+> newRemoteState fname = return $ Remote fname []
+
+> getRemoteTypeName :: CTypeSpec -> Maybe String
+> getRemoteTypeName (CSUType (CStruct CStructTag (Just n) _ _ _) _) = Just $ "struct_" ++ (identToString n)
+> getRemoteTypeName (CSUType (CStruct CUnionTag (Just n) _ _ _) _) = Just $ "union_" ++ (identToString n)
+> getRemoteTypeName (CEnumType (CEnum (Just n) _ _ _) _) = Just $ "enum_" ++ (identToString n)
+> getRemoteTypeName (CTypeDef n _) = Just $ identToString n
+> getRemoteTypeName _ = Nothing
+
+> mkRemoteDecl :: CDecl -> [CDerivedDeclr] -> String -> Maybe CDecl
+> mkRemoteDecl d@(CDecl specs inits ni) ders v =
+> let s = getTypeSpec specs
+> in case s of
+> (CSUType (CStruct CStructTag name _ _ ni2) ni3) -> Just $ mkCDecl (CSUType (CStruct CStructTag name Nothing [] ni2) ni3) ders v ni
+> (CSUType (CStruct CUnionTag name _ _ ni2) ni3) -> Just $ mkCDecl (CSUType (CStruct CUnionTag name Nothing [] ni2) ni3) ders v ni
+> (CEnumType (CEnum name _ _ ni2) ni3) -> Just $ mkCDecl (CEnumType (CEnum name Nothing [] ni2) ni3) ders v ni
+> (CTypeDef name ni2) -> Just $ mkCDecl (CTypeDef name ni2) ders v ni
+> _ -> Nothing
+
+> getFieldTypeName :: CDecl -> RemoteT String
+> getFieldTypeName d@(CDecl specs declrs ni) = do
+> let t = getTypeSpec specs
+> ds = getCDeclrsFromList declrs
+> ptrs = if null ds then [] else getDerivedPtrs $ head ds
+> tname = getRemoteTypeName t
+> ptrStrings = join $ map (\_ -> "_ptr") ptrs
+> when (isNothing tname) $ invalid ("parameter '" ++ (show $ pretty d) ++ "' does not have an known encoding type") ni
+> return ((fromJust tname) ++ ptrStrings)
+
+typeof(expr)
+
+CTypeOfType CDecl NodeInfo
+
+
+> mkEncodeBlock :: NodeInfo -> Bool -> String -> String -> [CStat]
+> mkEncodeBlock ni isPtr typeName fieldName = mkStmtsFromCLines ni $
+> "{ \
+> \ ret = gs_encode_"++typeName++"(buf, "++fieldName++", "++(if isPtr then "" else "&")++"x->"++fieldName++"); \
+> \ if(ret != 0) \
+> \ { \
+> \ return ret; \
+> \ } \
+> \}"
+
+> mkEncodeStmts :: [CDecl] -> NodeInfo -> RemoteT CStat
+> mkEncodeStmts fields ni = do
+> types <- mapM getFieldTypeName fields
+> let vars = map getVarName fields
+> return $ mkCompoundWithDecls Nothing [genCDecl "gs_ret_t" "ret" ni]
+> ((concat (zipWith (mkEncodeBlock ni False) types vars)) ++ [mkStmtFromC ni "return ret;"]) ni
+
+> mkEncodeFun :: CDecl -> String -> [CDecl] -> NodeInfo -> RemoteT CExtDecl
+> mkEncodeFun decl sname fields ni = do
+> stmts <- mkEncodeStmts fields ni
+> let tparam = mkRemoteDecl decl [(CPtrDeclr [] ni)] "x"
+> when (isNothing tparam) $ invalid "not a known encoding type" ni
+> return $ mkFunDef (CTypeDef (newIdent "gs_ret_t" ni) ni)
+> [(CStorageSpec (CStatic ni)), (CTypeQual (CInlineQual ni))]
+> ("gs_encode_" ++ sname)
+> [genCDecl "gs_buffer_t" "buf" ni,
+> genCDecl "gs_string_t" "varname" ni,
+> fromJust tparam]
+> stmts
+
+> mkDecodeBlock :: NodeInfo -> Bool -> String -> String -> [CStat]
+> mkDecodeBlock ni isPtr typeName fieldName = mkStmtsFromCLines ni $
+> "{ \
+> \ ret = gs_decode_"++typeName++"(buf, "++fieldName++", "++(if isPtr then "" else "&")++"x->"++fieldName++"); \
+> \ if(ret != 0) \
+> \ { \
+> \ return ret; \
+> \ } \
+> \}"
+
+> mkDecodeStmts :: [CDecl] -> NodeInfo -> RemoteT CStat
+> mkDecodeStmts fields ni = do
+> types <- mapM getFieldTypeName fields
+> let vars = map getVarName fields
+> return $ mkCompoundWithDecls Nothing [genCDecl "gs_ret_t" "ret" ni]
+> ((concat (zipWith (mkDecodeBlock ni False) types vars)) ++ [mkStmtFromC ni "return ret;"]) ni
+
+> mkDecodeFun :: CDecl -> String -> [CDecl] -> NodeInfo -> RemoteT CExtDecl
+> mkDecodeFun decl sname fields ni = do
+> stmts <- mkDecodeStmts fields ni
+> let tparam = mkRemoteDecl decl [(CPtrDeclr [] ni)] "x"
+> when (isNothing tparam) $ invalid "not a known encoding type" ni
+> return $ mkFunDef (CTypeDef (newIdent "gs_ret_t" ni) ni)
+> [(CStorageSpec (CStatic ni)), (CTypeQual (CInlineQual ni))]
+> ("gs_decode_" ++ sname)
+> [genCDecl "gs_buffer_t" "buf" ni,
+> genCDecl "gs_string_t" "varname" ni,
+> fromJust tparam]
+> stmts
+
+> mkSizeBlock :: NodeInfo -> Bool -> String -> String -> [CStat]
+> mkSizeBlock ni isPtr typeName fieldName = mkStmtsFromCLines ni $
+> "{ \
+> \ size += gs_encode_size_"++typeName++"("++fieldName++", "++(if isPtr then "" else "&")++"x->"++fieldName++"); \
+> \}"
+
+> mkSizeStmts :: [CDecl] -> NodeInfo -> RemoteT CStat
+> mkSizeStmts fields ni = do
+> types <- mapM getFieldTypeName fields
+> let vars = map getVarName fields
+> return $ mkCompoundWithDecls Nothing [genCDecl "uint64_t" "size" ni]
+> ([mkStmtFromC ni "size = 0;"] ++ ((concat (zipWith (mkSizeBlock ni False) types vars))) ++ [mkStmtFromC ni "return size;"]) ni
+
+> mkSizeFun :: CDecl -> String -> [CDecl] -> NodeInfo -> RemoteT CExtDecl
+> mkSizeFun decl sname fields ni = do
+> stmts <- mkSizeStmts fields ni
+> let tparam = mkRemoteDecl decl [(CPtrDeclr [] ni)] "x"
+> when (isNothing tparam) $ invalid "not a known encoding type" ni
+> return $ mkFunDef (CTypeDef (newIdent "uint64_t" ni) ni)
+> [(CStorageSpec (CStatic ni)), (CTypeQual (CInlineQual ni))]
+> ("gs_encode_size_" ++ sname)
+> [genCDecl "gs_string_t" "varname" ni,
+> fromJust tparam]
+> stmts
+
+
+> registerStruct :: CDecl -> RemoteT [CExtDecl]
+> registerStruct d@(CDecl specs inits ni) = do
+> let si = getStructInfo d
+> (Just (_, fields)) = si
+> s = getRemoteTypeName (getTypeSpec specs)
+> sname = fromJust s
+> allFields = join $ map splitDecls fields
+> when (isNothing s) $ invalid ("cannot define a remote struct without a name\n") ni
+> if (structSpecHasFields (head $ filter isStructTypeSpec specs)) then do
+> let newS = CDeclExt $ CDecl (filter (not . isRemoteSpec) specs) inits ni
+> enc <- mkEncodeFun d sname allFields ni
+> size <- mkSizeFun d sname allFields ni
+> dec <- mkDecodeFun d sname allFields ni
+> return [newS, size, enc, dec]
+> else return []
+
+ init = mkInitFun d
+ dest = mkDestroyFun d
+
+> transDecl :: CExtDecl -> RemoteT [CExtDecl]
+> transDecl e@(CDeclExt d@(CDecl specs inits ni))
+> | any isRemoteSpec specs = registerStruct d
+> | otherwise = return []
+
+> getFileName :: RemoteT String
+> getFileName = do
+> w <- get
+> return $ filename w
+
+> getFilePosStr :: NodeInfo -> RemoteT String
+> getFilePosStr (NodeInfo p _ _) = do
+> fname <- getFileName
+> return (fname ++ ":" ++ (show $ posRow p) ++ ":" ++ (show $ posColumn p))
+
+> type RemoteT = StateT Remote IO
+
+> invalid :: String -> NodeInfo -> RemoteT ()
+> invalid msg ni = do
+> fstr <- getFilePosStr ni
+> error (fstr ++ ": Invalid grayskull usage: " ++ msg)
+
+> inRemoteStructs :: CDecl -> Bool
+> inRemoteStructs _ = True
+
+> isRemoteFunDef :: CFunDef -> Bool
+> isRemoteFunDef (CFunDef specs declr decls stmt ni) = any isRemoteSpec specs
+
+> filterOutRemoteSpec :: [CDeclSpec] -> [CDeclSpec]
+> filterOutRemoteSpec = filter (not . isRemoteSpec)
+
+> mkStubDecl :: String -> (CTypeSpec, [CDerivedDeclr]) -> [CDecl] -> CDecl
+> mkStubDecl fname (retType, retDerived) params = mkFunDecl ("remote_" ++ fname) retType retDerived params
+
+> mkGSRetType :: NodeInfo -> CTypeSpec
+> mkGSRetType ni = (CTypeDef (newIdent "gs_ret_t" ni) ni)
+
+> mkGSBufferType :: NodeInfo -> CTypeSpec
+> mkGSBufferType ni = (CTypeDef (newIdent "gs_buffer_t" ni) ni)
+
+> mkSkelDecl :: NodeInfo -> String -> CDecl
+> mkSkelDecl ni fname = mkFunDecl ("__service_"++fname) (mkGSRetType ni) [] [mkCDecl (mkGSBufferType ni) [(CPtrDeclr [] ni)] "buffer" ni]
+
+> checkRemoteParams :: NodeInfo -> [CDecl] -> RemoteT ()
+> checkRemoteParams ni [inputdecl, outputdecl] = do
+> let inNI = nodeInfo inputdecl
+> inName = identToString $ getCDeclName inputdecl
+> outNI = nodeInfo outputdecl
+> outName = identToString $ getCDeclName outputdecl
+> when (not $ inRemoteStructs inputdecl) $ invalid ("input parameter '"++inName++"' cannot be encoded, must use a __remote type") inNI
+> when (not $ inRemoteStructs outputdecl) $ invalid ("output parameter '"++outName++"' cannot be encoded, must use a __remote type") outNI
+> let (CDecl specs initdeclrs ni) = outputdecl
+> ptrs = filter isDerivedPtr $ join $ map getDerivedDeclrs initdeclrs
+> when ((length ptrs) /= 1) $ invalid ("output parameter '"++outName++"' must be a pointer to type") outNI
+> return ()
+
+> checkRemoteParams ni _ = do
+> invalid "only two parameters allowed for a __remote declaration" ni
+> return ()
+
+> isGSReturnType :: CTypeSpec -> Bool
+> isGSReturnType (CTypeDef (Ident name _ _) _) = name == "gs_ret_t"
+
+> checkRemoteReturn :: (CTypeSpec, [CDerivedDeclr]) -> RemoteT ()
+> checkRemoteReturn (retType, retDerived) = do
+> when (not $ isGSReturnType retType) $ invalid "__remote function must have a return type of gs_ret_t" (nodeInfo retType)
+> return ()
+
+> registerRemoteDecl :: CExtDecl -> RemoteT [CExtDecl]
+> registerRemoteDecl e@(CDeclExt d@(CDecl specs inits ni))
+
+> | isStructDecl d && (any isRemoteSpec specs) = transDecl e
+> | isFunDecl d && (any isRemoteSpec specs) = do
+> let (fname, returnType, params) = splitFunDecl d
+> newspecs = filterOutRemoteSpec specs
+> ni = nodeInfo e
+
+> -- only two params allowed right now: input and pointer to output
+> checkRemoteParams ni params
+
+> checkRemoteReturn returnType
+
+> let [inputdecl, outputdecl] = params
+> origDecl = CDeclExt $ (CDecl newspecs inits ni)
+> stubDecl = CDeclExt $ addBlockingTQ $ mkStubDecl fname returnType params
+> skelDecl = CDeclExt $ addBlockingTQ $ mkSkelDecl ni fname
+
+> return [origDecl, stubDecl, skelDecl]
+> | otherwise = return [e]
+
+> registerRemoteDecl e = return [e]
+
+> registerRemoteDecls :: CTranslUnit -> RemoteT CTranslUnit
+> registerRemoteDecls (CTranslUnit decls ni) = do
+> newdecls <- liftM concat $ sequence $ map registerRemoteDecl decls
+> return $ CTranslUnit newdecls ni
+
+> data ParserOpts = Pretty | Help | Include String | Report String | Outfile String | Header
+
+> getIncludes :: [ParserOpts] -> [String]
+> getIncludes ((Include s):ps) = ("-I" ++ s):(getIncludes ps)
+> getIncludes (_:ps) = getIncludes ps
+> getIncludes [] = []
+
+> getReportFilename :: [ParserOpts] -> Maybe String
+> getReportFilename ((Report s):ps) = Just s
+> getReportFilename (_:ps) = getReportFilename ps
+> getReportFilename [] = Nothing
+
+> getOutfile :: [ParserOpts] -> Maybe String
+> getOutfile ((Outfile s):ps) = Just s
+> getOutfile (_:ps) = getOutfile ps
+> getOutfile [] = Nothing
+
+> parserOpts :: [OptDescr ParserOpts]
+> parserOpts =
+> [ Option ['p'] ["pretty"] (NoArg Pretty)
+> "output in pretty form without source line macros"
+> , Option ['I'] ["include"] (ReqArg (\s -> Include s) "<include path>")
+> "include path for preprocessor"
+> , Option ['h','?'] ["help"] (NoArg Help)
+> "help text"
+> , Option ['r'] ["report"] (ReqArg (\s -> Report s) "<report filename>")
+> "filename to use when reporting errors"
+> , Option ['o'] ["outfile"] (ReqArg (\s -> Outfile s) "<output file>")
+> "filename to write translated C code"
+> , Option ['j'] ["header"] (NoArg Header)
+> "parse header file instead of source"
+> ]
+
+> optPretty :: ParserOpts -> Bool
+> optPretty (Pretty) = True
+> optPretty _ = False
+
+> optHelp :: ParserOpts -> Bool
+> optHelp (Help) = True
+> optHelp _ = False
+
+> optHeader :: ParserOpts -> Bool
+> optHeader (Header) = True
+> optHeader _ = False
+
+> parseRemoteHeader :: FilePath -> Maybe FilePath -> FilePath -> IO ()
+> parseRemoteHeader headerfile report outfuile = return ()
+
+> mkStubBlock :: String -> String -> String -> String -> NodeInfo -> [CStat]
+> mkStubBlock inTypeName inName outTypeName outName ni = mkStmtsFromCLines ni $
+> "{ \
+> \ ret = gs_encode_maxsize_"++inTypeName++"(&maxsize); \
+> \ if(ret != GS_SUCCESS) \
+> \ { \
+> \ return ret; \
+> \ } \
+> \ ret = gs_buffer_allocate(&buffer, maxsize); \
+> \ if(ret != GS_SUCCESS) \
+> \ { \
+> \ return ret; \
+> \ } \
+> \ ret = gs_encode_"++inTypeName++"(buffer, "++inName++"); \
+> \ if(ret != GS_SUCCESS) \
+> \ { \
+> \ gs_buffer_free(buffer); \
+> \ return ret; \
+> \ } \
+> \ ret = gs_decode_maxsize_"++outTypeName++"(&max_recvsize); \
+> \ if(ret != GS_SUCCESS) \
+> \ { \
+> \ gs_buffer_free(buffer); \
+> \ return ret; \
+> \ } \
+> \ ret = gs_buffer_allocate(&recv_buffer, max_recvsize); \
+> \ if(ret != GS_SUCCESS) \
+> \ { \
+> \ gs_buffer_free(buffer); \
+> \ return ret; \
+> \ } \
+> \ ret = gs_msg_send_recv(id, buffer, recv_buffer); \
+> \ if(ret != GS_SUCCESS) \
+> \ { \
+> \ gs_buffer_free(buffer); \
+> \ gs_buffer_free(recv_buffer); \
+> \ return ret; \
+> \ } \
+> \ ret = gs_decode_"++outTypeName++"(buffer, "++outName++"); \
+> \ gs_buffer_free(buffer); \
+> \ gs_buffer_free(recv_buffer); \
+> \ return ret; \
+> \}"
+
+> mkStubStmts :: [CDecl] -> NodeInfo -> CStat
+> mkStubStmts params ni =
+> let [inparam, outparam] = params
+> (Ident inParamName _ _) = getCDeclName inparam
+> (Ident outParamName _ _) = getCDeclName outparam
+> inTypeName = canonCDecl inparam
+> outTypeName = canonCDecl outparam
+
+> in mkCompoundWithDecls Nothing
+
+> -- declarations
+> [genCDecl "gs_buffer_t" "buffer" ni,
+> genCDecl "gs_buffer_t" "recv_buffer" ni,
+> genCDecl "int" "maxsize" ni,
+> genCDecl "gs_ret_t" "ret" ni]
+
+> (mkStubBlock inTypeName inParamName outTypeName outParamName ni)
+> ni
+
+> mkStubFun :: CFunDef -> CExtDecl
+> mkStubFun fundef =
+> let fname = getFunDefName fundef
+> params = getFunDefParams fundef
+> ni = nodeInfo fundef
+> in mkFunDef (CTypeDef (newIdent "gs_ret_t" ni) ni) -- return type
+> (filterOutRemoteSpec $ getDeclSpecs fundef) -- get the storage specs for the function
+> ("remote_" ++ fname) -- the function name for the stub
+> ((genCDecl "gs_node_id" "id" ni) : params) -- parameters
+> (mkStubStmts params ni)
+
+> mkSkelBlock :: String -> String -> String -> String -> String -> NodeInfo -> [CStat]
+> mkSkelBlock fname inTypeName inName outTypeName outName ni = mkStmtsFromCLines ni $
+> "{ \
+> \ ret = gs_decode_"++inTypeName++"(buffer, "++inName++"); \
+> \ if(ret != GS_SUCCESS) \
+> \ { \
+> \ return ret; \
+> \ } \
+> \ ret = gs_encode_maxsize_"++outTypeName++"(&max_respsize); \
+> \ if(ret != GS_SUCCESS) \
+> \ { \
+> \ return ret; \
+> \ } \
+> \ ret = gs_buffer_allocate(resp_buffer, max_respsize); \
+> \ if(ret != GS_SUCCESS) \
+> \ { \
+> \ return ret; \
+> \ } \
+> \ ret = "++fname++"("++inName++", &"++outName++"); \
+> \ if(ret != GS_SUCCESS) \
+> \ { \
+> \ return ret; \
+> \ } \
+> \ ret = gs_encode_"++outTypeName++"(resp_buffer, "++outName++"); \
+> \ if(ret != GS_SUCCESS) \
+> \ { \
+> \ return ret; \
+> \ } \
+> \ return ret; \
+> \}"
+
+> mkSkelStmts :: String -> [CDecl] -> NodeInfo -> CStat
+> mkSkelStmts fname params ni =
+> let [inparam, outparam] = params
+> (Ident inParamName _ _) = getCDeclName inparam
+> (Ident outParamName _ _) = getCDeclName outparam
+> inTypeName = canonCDecl inparam
+> outTypeName = canonCDecl outparam
+
+> in mkCompoundWithDecls Nothing
+
+> -- declarations
+> [genCDecl "int" "maxsize" ni,
+> inparam, outparam,
+> genCDecl "gs_ret_t" "ret" ni]
+
+> -- stmts
+> (mkSkelBlock fname inTypeName inParamName outTypeName outParamName ni)
+> ni
+
+
+> mkSkelFun :: CFunDef -> CExtDecl
+> mkSkelFun fundef =
+> let fname = getFunDefName fundef
+> params = getFunDefParams fundef
+> ni = nodeInfo fundef
+> in mkFunDef (CTypeDef (newIdent "gs_ret_t" ni) ni) -- return type
+> (filterOutRemoteSpec $ getDeclSpecs fundef) -- get the storage specs for the function
+> ("__service_" ++ fname) -- the function name for the stub
+> [genCDecl "gs_buffer_t *" "buffer" ni,
+> genCDecl "gs_buffer_t *" "resp_buffer" ni]
+> (mkSkelStmts fname params ni)
+
+> transformRemote :: CExtDecl -> RemoteT [CExtDecl]
+> transformRemote e@(CFDefExt funDef)
+> | isRemoteFunDef funDef = do
+> let re = removeRemoteSpecFromFunDef e
+> stub = mkStubFun funDef
+> rstub = removeRemoteSpecFromFunDef stub
+> skel = mkSkelFun funDef
+> rskel = removeRemoteSpecFromFunDef skel
+> return [re, rstub, rskel]
+> | otherwise = return [e]
+> transformRemote e = return [e]
+
+> transformR :: CTranslUnit -> RemoteT CTranslUnit
+> transformR (CTranslUnit decls ni) = do
+> newdecls <- liftM concat $ sequence $ map transformRemote decls
+> return $ CTranslUnit newdecls ni
+
+> generateAST :: FilePath -> IO CTranslUnit
+> generateAST input_file = do
+> input_stream <- readInputStream input_file
+> let parse_result = parseC input_stream (position 0 input_file 1 1)
+> case parse_result of
+> Left parse_err -> error (show parse_err)
+> Right ast -> return ast
+
+> parseRemote :: Bool -> [String] -> FilePath -> Maybe FilePath -> FilePath -> IO ()
+> parseRemote p includes outfile report f = do
+> let r = if isJust report then fromJust report else f
+> w <- newRemoteState r
+> ctu <- generateAST f
+> (ctuWithDecls, w) <- runStateT (registerRemoteDecls ctu) w
+> (transCTU, w) <- runStateT (transformR ctuWithDecls) w
+> if p then ((writeFile outfile) . show . pretty) transCTU
+> else ((writeFile outfile) . show . serialize) transCTU
+> appendFile outfile "\n\n"
+> return ()
+
+> main :: IO ()
+> main = do
+> args <- getArgs
+> let (opts, files, errs) = getOpt RequireOrder parserOpts args
+> pretty = any optPretty opts
+> help = any optHelp opts
+> includes = getIncludes opts
+> outfile = getOutfile opts
+> pheader = any optHeader opts
+> report = getReportFilename opts
+> header = "Usage: gs-remote-parser [OPTIONS...] files..."
+>
+> when (not $ null errs) $ ioError $ userError ((concat errs) ++
+> (usageInfo header parserOpts))
+>
+> when help $ do { putStrLn $ usageInfo header parserOpts ; exitWith (ExitFailure 1) }
+> when (isNothing outfile) $ ioError $ userError "No output file specified."
+
+> when pheader $ do { mapM_ (\f -> parseRemoteHeader f report (fromJust outfile)) files ; exitWith (ExitSuccess) }
+> mapM_ (parseRemote pretty includes (fromJust outfile) report) files
+
+vim: ts=8 sts=4 sw=4 expandtab
diff --git a/code/src/gsl/parser/module.mk.in b/code/src/gsl/parser/module.mk.in
index 4453ef1..ab1ed82 100644
--- a/code/src/gsl/parser/module.mk.in
+++ b/code/src/gsl/parser/module.mk.in
@@ -1,6 +1,6 @@
DIR := parser
-HSSRC += $(DIR)/gs-parser.lhs \
+HSSRC += $(DIR)/gs-blocking-parser.lhs \
$(DIR)/CGen.lhs \
$(DIR)/CParse.lhs \
$(DIR)/CUtils.lhs \
@@ -8,9 +8,13 @@ HSSRC += $(DIR)/gs-parser.lhs \
$(DIR)/Walker.lhs \
$(DIR)/ContextGen.lhs \
$(DIR)/Serialize.hs \
- $(DIR)/Header.lhs
+ $(DIR)/Header.lhs \
+ $(DIR)/gs-remote-parser.lhs
-HSBINSRC += $(DIR)/gs-parser.lhs
+HSBINSRC += $(DIR)/gs-blocking-parser.lhs $(DIR)/gs-remote-parser.lhs
+
+MODNAME_$(DIR)/gs-blocking-parser.lhs = BlockingParser
+MODNAME_$(DIR)/gs-remote-parser.lhs = RemoteParser
clean::
- rm -rf *.o *.hi gs-parser
+ rm -rf *.o *.hi gs-blocking-parser gs-remote-parser
diff --git a/code/src/gsl/tests/correctness/funptrs.gs b/code/src/gsl/tests/correctness/funptrs.gs
index 504a2ea..96e3766 100644
--- a/code/src/gsl/tests/correctness/funptrs.gs
+++ b/code/src/gsl/tests/correctness/funptrs.gs
@@ -15,6 +15,8 @@ typedef struct
int b;
} mytype;
+typedef mytype ttype;
+
static __blocking int blocking1(int a)
{
int ret;
@@ -37,6 +39,18 @@ static __blocking int do_mtype_blocking(mytype *t)
return t->p->myfun(t->b);
}
+static __blocking int do_ttype_blocking(ttype *t)
+{
+ return t->p->myfun(t->b);
+}
+
+typedef ttype atype;
+
+static __blocking int do_atype_blocking(atype *t)
+{
+ return t->p->myfun(t->b);
+}
+
static int done = 0;
static void *myptr;
@@ -74,6 +88,27 @@ int main(int argc, char *argv[])
{
gs_poll(NULL, 0);
}
+
+ done = 0;
+ t.p = &s;
+ t.b = 100;
+ do_ttype_blocking_post(&t, basic_cb, myptr, NULL, NULL, &id);
+
+ while(done == 0)
+ {
+ gs_poll(NULL, 0);
+ }
+
+ done = 0;
+ t.p = &s;
+ t.b = 100;
+ do_atype_blocking_post(&t, basic_cb, myptr, NULL, NULL, &id);
+
+ while(done == 0)
+ {
+ gs_poll(NULL, 0);
+ }
+
btest_finalize();
free(myptr);
diff --git a/code/src/gsl/tests/correctness/module.mk.in b/code/src/gsl/tests/correctness/module.mk.in
index 0ea4a77..238abf2 100644
--- a/code/src/gsl/tests/correctness/module.mk.in
+++ b/code/src/gsl/tests/correctness/module.mk.in
@@ -34,7 +34,10 @@ GSTESTSRC += $(DIR)/icpfor.gs \
$(DIR)/twofors.gs \
$(DIR)/threefors.gs \
$(DIR)/funptrs.gs \
- $(DIR)/nbfun.gs
+ $(DIR)/nbfun.gs \
+ $(DIR)/pprivate.gs \
+ $(DIR)/pshared.gs \
+ $(DIR)/pbranch-with-return.gs
GSHDR += $(DIR)/btest.gsh
hooks/post-receive
--
Grayskull Repository
1
0
[Gs-commits] Grayskull Repository branch, master, updated. git-migration-295-g633a91e
by noreply@mcs.anl.gov 16 Dec '09
by noreply@mcs.anl.gov 16 Dec '09
16 Dec '09
A ref change was pushed to the repository containing
the project "Grayskull Repository".
The branch, master has been updated
via 633a91e55dab62f2552b52e311b721ed6c097985 (commit)
via 0c4daab522ba0d4c3b3dc5f4a2d0595f8e6d7b1f (commit)
via d493a790c1b1b1b3767260e3a9b01d9da67a2376 (commit)
from 95873c5c5d7e07c2692a544706d2dd252a9619cd (commit)
Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.
- Log -----------------------------------------------------------------
commit 633a91e55dab62f2552b52e311b721ed6c097985
Author: Phil Carns <carns(a)mcs.anl.gov>
Date: Wed Dec 16 14:48:45 2009 -0500
bug fix to workload generator
commit 0c4daab522ba0d4c3b3dc5f4a2d0595f8e6d7b1f
Author: Phil Carns <carns(a)mcs.anl.gov>
Date: Wed Dec 16 14:34:34 2009 -0500
added program to generate benchmark workloads
commit d493a790c1b1b1b3767260e3a9b01d9da67a2376
Author: Phil Carns <carns(a)mcs.anl.gov>
Date: Wed Dec 16 13:36:47 2009 -0500
minor cleanup of cosd benchmark
-----------------------------------------------------------------------
Summary of changes:
.../cosd-prototype/test/cosd-bench-concurrent.gs | 20 +--
.../gsl/resources/cosd-prototype/test/module.mk.in | 2 +
.../resources/cosd-prototype/test/workload-gen.gs | 122 ++++++++++++++++++++
3 files changed, 131 insertions(+), 13 deletions(-)
create mode 100644 code/src/gsl/resources/cosd-prototype/test/workload-gen.gs
Diff of changes:
diff --git a/code/src/gsl/resources/cosd-prototype/test/cosd-bench-concurrent.gs b/code/src/gsl/resources/cosd-prototype/test/cosd-bench-concurrent.gs
index aa43467..7a9de2a 100644
--- a/code/src/gsl/resources/cosd-prototype/test/cosd-bench-concurrent.gs
+++ b/code/src/gsl/resources/cosd-prototype/test/cosd-bench-concurrent.gs
@@ -44,26 +44,23 @@ static __blocking int do_cosd_test(void)
uint64_t out_oid1;
uint64_t version;
- printf("Creating oid 1 (if it doesn't already exist)...\n");
ret = gs_cosd_create(1, &out_oid1);
- if(ret != 0 && ret != -EEXIST)
+ if(ret == -EEXIST)
+ {
+ printf("# operating on existing object.\n");
+ }
+ else if(ret != 0)
{
printf("Error creating oid=1: %d\n", ret);
return 1;
}
- printf("DONE\n");
- printf("Getting version number of oid 1...\n");
ret = gs_cosd_get_version(1, &version);
if(ret != 0)
{
printf("Error getting version number for oid=1: %d\n", ret);
return(1);
}
- printf("DONE: %llu\n", llu(version));
-
- ret = gs_cosd_dump();
- assert(ret == 0);
pwait
{
@@ -206,12 +203,11 @@ int main(int argc, char *argv[])
fclose(desc);
if(mode == 1)
- printf("Initializing cosd in poll-driven mode...\n");
+ printf("# Initializing cosd in poll-driven mode.\n");
else
- printf("Initializing cosd in thread-per-op mode...\n");
+ printf("# Initializing cosd in thread-per-op mode.\n");
gs_cosd_init(mode, argv[3]);
- printf("Done.\n");
gs_context_create(&ctx, 1, "cosd");
@@ -221,8 +217,6 @@ int main(int argc, char *argv[])
{
pc++;
gs_poll(ctx, 10000);
- fflush(NULL);
- printf("polled %d times...\n", pc);
}
gs_cosd_finalize();
diff --git a/code/src/gsl/resources/cosd-prototype/test/module.mk.in b/code/src/gsl/resources/cosd-prototype/test/module.mk.in
index 78bca02..b0f2de9 100644
--- a/code/src/gsl/resources/cosd-prototype/test/module.mk.in
+++ b/code/src/gsl/resources/cosd-prototype/test/module.mk.in
@@ -2,5 +2,7 @@ DIR := resources/cosd-prototype/test
GSTESTSRC += $(DIR)/cosd1.gs
GSTESTSRC += $(DIR)/cosd-bench-concurrent.gs
+GSTESTSRC += $(DIR)/workload-gen.gs
+
MODLIBS_$(DIR) = -lpthread @DB_LIB@
diff --git a/code/src/gsl/resources/cosd-prototype/test/workload-gen.gs b/code/src/gsl/resources/cosd-prototype/test/workload-gen.gs
new file mode 100644
index 0000000..37db00a
--- /dev/null
+++ b/code/src/gsl/resources/cosd-prototype/test/workload-gen.gs
@@ -0,0 +1,122 @@
+#include <stdio.h>
+#include <errno.h>
+#include <assert.h>
+#include <stdlib.h>
+
+#include "../../../include/gs.h"
+#include "../cosd-prototype.gsh"
+#include "gs-config.h"
+
+
+/*
+ * arguments:
+ * ./workload-gen <total size> <op size> <l|r>
+ */
+
+/* TODO: this needs to be in a header somewhere */
+#ifndef llu
+#if SIZEOF_LONG_INT == 4
+# define llu(x) (x)
+# define lld(x) (x)
+# define SCANF_lld lld
+#elif SIZEOF_LONG_INT == 8
+# define llu(x) (unsigned long long)(x)
+# define lld(x) (long long)(x)
+# define SCANF_lld ld
+#else
+# error Unexpected sizeof(long int)
+#endif
+#endif
+
+int main(int argc, char **argv)
+{
+ int64_t total_size = -1;
+ int64_t op_size = -1;
+ int random_flag = 0;
+ int op_count = 0;
+ int64_t* offset_array;
+ int i;
+ int64_t current_offset = 0;
+
+ if(argc != 4)
+ {
+ fprintf(stderr, "Usage: %s <total size> <op size> <l|r>\n",
+ argv[0]);
+ fprintf(stderr, " r=random, l=linear\n");
+ return(-1);
+ }
+
+#if SIZEOF_LONG_INT == 4
+ sscanf(argv[1], "%lld", &total_size);
+ sscanf(argv[2], "%lld", &op_size);
+#else
+ sscanf(argv[1], "%ld", &total_size);
+ sscanf(argv[2], "%ld", &op_size);
+#endif
+
+ if(total_size < 1 || op_size < 1)
+ {
+ fprintf(stderr, "Usage: %s <total size> <op size> <l|r>\n",
+ argv[0]);
+ fprintf(stderr, " r=random, l=linear\n");
+ return(-1);
+ }
+
+ if(strcmp(argv[3], "l") == 0)
+ random_flag = 0;
+ else if(strcmp(argv[3], "r") == 0)
+ random_flag = 1;
+ else
+ {
+ fprintf(stderr, "Usage: %s <total size> <op size> <l|r>\n",
+ argv[0]);
+ fprintf(stderr, " r=random, l=linear\n");
+ return(-1);
+ }
+
+ if(total_size % op_size != 0)
+ {
+ fprintf(stderr, "Error: sizes must be evenly divisible.\n");
+ return(-1);
+ }
+
+ op_count = total_size/op_size;
+
+ /* allocate one big array with all of the offset */
+ offset_array = malloc(op_count*sizeof(int64_t));
+ assert(offset_array);
+
+ for(i=0; i<op_count; i++)
+ {
+ offset_array[i] = current_offset;
+ current_offset+= op_size;
+ }
+
+ if(random_flag && op_count > 1)
+ {
+ for(i=0; i<(op_count-1); i++)
+ {
+ int j = i + rand() / (RAND_MAX / (op_count-i) + 1);
+ int64_t t = offset_array[j];
+ offset_array[j] = offset_array[i];
+ offset_array[i] = t;
+ }
+ }
+
+ printf("# <op> <offset> <size>\n");
+ for(i=0; i<op_count; i++)
+ {
+ printf("write\t%lld\t%lld\n", lld(offset_array[i]), lld(op_size));
+ }
+
+ return(0);
+}
+
+/*
+ * Local variables:
+ * c-indent-level: 4
+ * c-basic-offset: 4
+ * End:
+ *
+ * vim: ft=c ts=8 sts=4 sw=4 expandtab
+ */
hooks/post-receive
--
Grayskull Repository
1
0