mirror of https://github.com/BOINC/boinc.git
more GAHP code
This commit is contained in:
parent
9209a887cc
commit
18d0f1f4d9
|
@ -7989,3 +7989,10 @@ David 29 Dec 2012
|
|||
|
||||
client/
|
||||
gui_rpc_server_ops.cpp
|
||||
|
||||
David 29 Dec 2012
|
||||
- Condor: initial checkin of BOINC GAHP framework
|
||||
|
||||
samples/condor/
|
||||
boinc_gahp.cpp
|
||||
Makefile
|
||||
|
|
|
@ -22,7 +22,6 @@
|
|||
#else
|
||||
#include "config.h"
|
||||
#include <string>
|
||||
#include <set>
|
||||
#endif
|
||||
|
||||
#include "parse.h"
|
||||
|
@ -38,7 +37,6 @@
|
|||
|
||||
using std::vector;
|
||||
using std::string;
|
||||
using std::set;
|
||||
using std::deque;
|
||||
|
||||
NOTICES notices;
|
||||
|
|
|
@ -179,6 +179,14 @@ $earth = array(
|
|||
$astro_phys_chem = array(
|
||||
tra("Astronomy, Physics, and Chemistry"),
|
||||
array(
|
||||
array(
|
||||
"Asteroids@home",
|
||||
"http://asteroidsathome.net/boinc/",
|
||||
"Charles University in Prague",
|
||||
"Astrophysics",
|
||||
"The aim of the project is to derive shapes and spin for a significant part of the asteroid population. As input data, we use any asteroid photometry that is available. The results are asteroid convex shape models with the direction of the spin axis and the rotation period.",
|
||||
"asteroids_logo.jpg"
|
||||
),
|
||||
array(
|
||||
"Constellation",
|
||||
"http://aerospaceresearch.net/constellation/",
|
||||
|
@ -471,7 +479,7 @@ $math = array(
|
|||
"Chess960@home",
|
||||
"http://www.chess960athome.org/alpha/",
|
||||
tra("Chess-960.org"),
|
||||
tra("Game-playing"),
|
||||
tra("Game study"),
|
||||
tra("This project studies Chess 960, a variant of orthodox chess. In classical chess the starting position of the game never changes. In Chess 960, just before the start of every game, the initial configuration of the chess pieces is determined randomly."),
|
||||
"chess960athome.jpg"
|
||||
),
|
||||
|
|
|
@ -0,0 +1,4 @@
|
|||
all: boinc_gahp
|
||||
|
||||
boinc_gahp: boinc_gahp.cpp
|
||||
g++ -lpthread -o boinc_gahp boinc_gahp.cpp
|
|
@ -0,0 +1,269 @@
|
|||
// This file is part of BOINC.
|
||||
// http://boinc.berkeley.edu
|
||||
// Copyright (C) 2012 University of California
|
||||
//
|
||||
// BOINC 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 3 of the License, or (at your option) any later version.
|
||||
//
|
||||
// BOINC 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 BOINC. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
// BOINC GAHP (Grid ASCII Helper Protocol) daemon
|
||||
|
||||
#include <stdio.h>
|
||||
#include <pthread.h>
|
||||
#include <stdlib.h>
|
||||
#include <unistd.h>
|
||||
#include <string.h>
|
||||
#include <map>
|
||||
#include <set>
|
||||
#include <string>
|
||||
#include <vector>
|
||||
|
||||
using std::map;
|
||||
using std::pair;
|
||||
using std::set;
|
||||
using std::string;
|
||||
using std::vector;
|
||||
|
||||
bool async_mode = true;
|
||||
|
||||
// represents a command.
|
||||
// if out is NULL the command is in progress;
|
||||
// otherwise it's the output
|
||||
//
|
||||
struct COMMAND {
|
||||
char* in;
|
||||
char* out;
|
||||
};
|
||||
|
||||
typedef map<int, COMMAND*> COMMANDS;
|
||||
COMMANDS commands;
|
||||
|
||||
struct INFILE {
|
||||
char src_path[256];
|
||||
char dst_path[256];
|
||||
};
|
||||
|
||||
struct JOB {
|
||||
char job_name[256];
|
||||
vector<string> args;
|
||||
vector<INFILE> infiles;
|
||||
bool all_output_files;
|
||||
vector<string> outfiles;
|
||||
};
|
||||
|
||||
struct SUBMIT_REQ {
|
||||
char batch_name[256];
|
||||
char app_name[256];
|
||||
vector<JOB> jobs;
|
||||
};
|
||||
|
||||
void compute_md5(string& path) {
|
||||
}
|
||||
|
||||
// Get a list of the input files used by the batch.
|
||||
// Get their MD5s.
|
||||
// See if they're already on the server.
|
||||
// If not, upload them.
|
||||
//
|
||||
int process_input_files(SUBMIT_REQ& req) {
|
||||
unsigned int i, j;
|
||||
|
||||
// get the set of source paths w/o dups
|
||||
//
|
||||
set<string> files;
|
||||
for (i=0; i<req.jobs.size(); i++) {
|
||||
JOB& job = req.jobs[i];
|
||||
for (j=0; j<job.infiles.size(); j++) {
|
||||
INFILE infile = job.infiles[j];
|
||||
files.insert(infile.src_path);
|
||||
}
|
||||
}
|
||||
|
||||
// compute the MD5s of these files
|
||||
//
|
||||
map<string, string> md5s;
|
||||
set<string>::iterator iter = files.begin();
|
||||
while (iter != files.end()) {
|
||||
string s = *iter;
|
||||
compute_md5(s);
|
||||
iter++;
|
||||
}
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
||||
int parse_boinc_submit(COMMAND& c, char* p, SUBMIT_REQ& req) {
|
||||
strcpy(req.batch_name, strtok_r(NULL, " ", &p));
|
||||
strcpy(req.app_name, strtok_r(NULL, " ", &p));
|
||||
int njobs = atoi(strtok_r(NULL, " ", &p));
|
||||
for (int i=0; i<njobs; i++) {
|
||||
JOB job;
|
||||
strcpy(job.job_name, strtok_r(NULL, " ", &p));
|
||||
int nargs = atoi(strtok_r(NULL, " ", &p));
|
||||
for (int j=0; j<nargs; j++) {
|
||||
string arg = strtok_r(NULL, " ", &p);
|
||||
job.args.push_back(arg);
|
||||
}
|
||||
int ninfiles = atoi(strtok_r(NULL, " ", &p));
|
||||
for (int j=0; j<ninfiles; j++) {
|
||||
INFILE infile;
|
||||
strcpy(infile.src_path, strtok_r(NULL, " ", &p));
|
||||
strcpy(infile.dst_path, strtok_r(NULL, " ", &p));
|
||||
job.infiles.push_back(infile);
|
||||
}
|
||||
char* q = strtok_r(NULL, " ", &p);
|
||||
if (!strcmp(q, "ALL")) {
|
||||
job.all_output_files = true;
|
||||
} else {
|
||||
job.all_output_files = false;
|
||||
int noutfiles = atoi(q);
|
||||
for (int j=0; j<noutfiles; j++) {
|
||||
string outfile = strtok_r(NULL, " ", &p);
|
||||
job.outfiles.push_back(outfile);
|
||||
}
|
||||
}
|
||||
req.jobs.push_back(job);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
int submit_jobs(SUBMIT_REQ req) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
void handle_boinc_submit(COMMAND& c, char* p) {
|
||||
SUBMIT_REQ req;
|
||||
int retval;
|
||||
retval = parse_boinc_submit(c, p, req);
|
||||
process_input_files(req);
|
||||
submit_jobs(req);
|
||||
}
|
||||
|
||||
void* handle_command_aux(void* q) {
|
||||
COMMAND &c = *((COMMAND*)q);
|
||||
char *p;
|
||||
|
||||
strtok_r(c.in, " ", &p);
|
||||
char* cmd = strtok_r(NULL, " ", &p);
|
||||
char* id = strtok_r(NULL, " ", &p);
|
||||
if (!strcmp(cmd, "BOINC_SUBMIT")) {
|
||||
handle_boinc_submit(c, p);
|
||||
} else {
|
||||
sleep(10);
|
||||
char buf[256];
|
||||
sprintf(buf, "handled command %s", c.in);
|
||||
c.out = strdup(buf);
|
||||
}
|
||||
return NULL;
|
||||
}
|
||||
|
||||
int handle_command(COMMAND& c) {
|
||||
char cmd[256];
|
||||
int id;
|
||||
|
||||
// Handle synchronous commands
|
||||
//
|
||||
sscanf(c.in, "%s", cmd);
|
||||
if (!strcmp(cmd, "VERSION")) {
|
||||
printf("1.0\n");
|
||||
} else if (!strcmp(cmd, "QUIT")) {
|
||||
exit(0);
|
||||
} else if (!strcmp(cmd, "RESULTS")) {
|
||||
sscanf(c.in, "%s %d", cmd, &id);
|
||||
COMMANDS::iterator i = commands.find(id);
|
||||
if (i == commands.end()) {
|
||||
printf("command %d not found\n", id);
|
||||
return 0;
|
||||
}
|
||||
COMMAND *c2 = i->second;
|
||||
if (c2->out) {
|
||||
printf("command %d result: %s\n", id, c2->out);
|
||||
free(c2->out);
|
||||
free(c2->in);
|
||||
free(c2);
|
||||
commands.erase(i);
|
||||
} else {
|
||||
printf("command %d not finished\n", id);
|
||||
}
|
||||
return 0;
|
||||
} else {
|
||||
|
||||
// Handle asynchronous commands
|
||||
//
|
||||
int n = sscanf(c.in, "%s %d", cmd, &id);
|
||||
if (n != 2) {
|
||||
fprintf(stderr, "invalid command: %s\n", c.in);
|
||||
return -1;
|
||||
}
|
||||
COMMAND *cp = new COMMAND;
|
||||
cp->in = c.in;
|
||||
cp->out = NULL;
|
||||
printf("inserting cmd %d\n", id);
|
||||
commands.insert(pair<int, COMMAND*>(id, cp));
|
||||
if (async_mode) {
|
||||
pthread_t thread_handle;
|
||||
pthread_attr_t thread_attrs;
|
||||
pthread_attr_init(&thread_attrs);
|
||||
pthread_attr_setstacksize(&thread_attrs, 32768);
|
||||
int retval = pthread_create(
|
||||
&thread_handle, &thread_attrs, &handle_command_aux, cp
|
||||
);
|
||||
if (retval) {
|
||||
fprintf(stderr, "can't create thread\n");
|
||||
return -1;
|
||||
}
|
||||
} else {
|
||||
handle_command_aux(cp);
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
// read a line from stdin (possibly very long).
|
||||
// Return it in a malloc'd buffer
|
||||
//
|
||||
char* get_cmd() {
|
||||
static const int buf_inc = 16384;
|
||||
char* p = (char*)malloc(buf_inc);
|
||||
if (!p) return NULL;
|
||||
int len = 0;
|
||||
int buf_size = buf_inc;
|
||||
while (1) {
|
||||
char c = fgetc(stdin);
|
||||
if (c == EOF) {
|
||||
return NULL;
|
||||
}
|
||||
if (c == '\n') {
|
||||
p[len] = 0;
|
||||
return p;
|
||||
}
|
||||
p[len++] = c;
|
||||
if (len == buf_size) {
|
||||
p = (char*)realloc(p, len+buf_inc);
|
||||
buf_size += buf_inc;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
int main() {
|
||||
char* p;
|
||||
int retval;
|
||||
while (1) {
|
||||
p = get_cmd();
|
||||
if (p == NULL) break;
|
||||
COMMAND c;
|
||||
c.in = p;
|
||||
retval = handle_command(c);
|
||||
if (retval) break;
|
||||
}
|
||||
}
|
|
@ -0,0 +1,73 @@
|
|||
// This file is part of BOINC.
|
||||
// http://boinc.berkeley.edu
|
||||
// Copyright (C) 2012 University of California
|
||||
//
|
||||
// BOINC 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 3 of the License, or (at your option) any later version.
|
||||
//
|
||||
// BOINC 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 BOINC. If not, see <http://www.gnu.org/licenses/>.
|
||||
|
||||
#include <curl/curl.h>
|
||||
#include <stdio.h>
|
||||
|
||||
int do_http_post(const char* url) {
|
||||
CURL *curl;
|
||||
CURLcode res;
|
||||
|
||||
struct curl_httppost *formpost=NULL;
|
||||
struct curl_httppost *lastptr=NULL;
|
||||
struct curl_slist *headerlist=NULL;
|
||||
|
||||
curl = curl_easy_init();
|
||||
if (!curl) {
|
||||
return -1;
|
||||
}
|
||||
|
||||
curl_formadd(&formpost, &lastptr,
|
||||
CURLFORM_COPYNAME, "sendfile",
|
||||
CURLFORM_FILE, "curl.cpp",
|
||||
CURLFORM_END
|
||||
);
|
||||
curl_formadd(&formpost, &lastptr,
|
||||
CURLFORM_COPYNAME, "filename",
|
||||
CURLFORM_COPYCONTENTS, "curl.cpp",
|
||||
CURLFORM_END
|
||||
);
|
||||
curl_formadd(&formpost, &lastptr,
|
||||
CURLFORM_COPYNAME, "sendfile2",
|
||||
CURLFORM_FILE, "boinc_gahp.cpp",
|
||||
CURLFORM_END
|
||||
);
|
||||
curl_formadd(&formpost, &lastptr,
|
||||
CURLFORM_COPYNAME, "filename2",
|
||||
CURLFORM_COPYCONTENTS, "boinc_gahp.cpp",
|
||||
CURLFORM_END
|
||||
);
|
||||
|
||||
headerlist = curl_slist_append(headerlist, "Expect:");
|
||||
curl_easy_setopt(curl, CURLOPT_URL, url);
|
||||
curl_easy_setopt(curl, CURLOPT_USERAGENT, "BOINC Condor adapter");
|
||||
curl_easy_setopt(curl, CURLOPT_HTTPPOST, formpost);
|
||||
|
||||
res = curl_easy_perform(curl);
|
||||
if (res != CURLE_OK) {
|
||||
fprintf(stderr, "CURL error: %s\n", curl_easy_strerror(res));
|
||||
}
|
||||
|
||||
curl_easy_cleanup(curl);
|
||||
curl_formfree(formpost);
|
||||
curl_slist_free_all(headerlist);
|
||||
return 0;
|
||||
}
|
||||
|
||||
int main() {
|
||||
do_http_post("http://isaac.ssl.berkeley.edu/foobar.php");
|
||||
}
|
Loading…
Reference in New Issue