/Users/kmartin/Documents/files/code/cpp/OScpp/COIN-OS/OS/applications/amplClient/OSAmplClient.cpp

Go to the documentation of this file.
00001 
00040 #include "OSCoinSolver.h"
00041 #include "OSConfig.h"
00042 #include "OSnl2osil.h"
00043 #include "OSiLReader.h"
00044 #include "OSrLReader.h"
00045 #include "OSiLWriter.h"
00046 #include "OSrLWriter.h"
00047 #include "OSInstance.h"
00048 #include "OSResult.h"
00049 #ifdef COIN_HAS_LINDO    
00050 #include "OSLindoSolver.h"
00051 #endif 
00052 #ifdef COIN_HAS_IPOPT    
00053 #include "OSIpoptSolver.h"
00054 #endif  
00055 #include "OSFileUtil.h"
00056 #include "OSDefaultSolver.h"
00057 #include "OSSolverAgent.h"
00058 #include "OShL.h"
00059 #include "OSErrorClass.h"
00060 #include <sstream>
00061 
00062 #ifdef HAVE_CSTRING
00063 # include <cstring>
00064 #else
00065 # ifdef HAVE_STRING_H
00066 #  include <string.h>
00067 # else
00068 #  error "don't have header file for string"
00069 # endif
00070 #endif
00071 
00072 
00073 //AMPL includes must be last.
00074 #include <asl.h>
00075 using std::cerr;
00076 using std::cout;
00077 using std::endl;
00078 
00079 
00080 int main(int argc, char **argv)
00081 {
00082         char *stub;
00083         // set AMPL structures
00084         ASL *asl;
00085         asl = ASL_alloc(ASL_read_fg);
00086     stub = argv[1];
00087         jac0dim((char*)stub, (fint)strlen(stub));
00088         OSnl2osil *nl2osil = NULL;
00089         //initialize object with stub -- the nl file
00090         nl2osil = new OSnl2osil( stub);
00091         // create an osinstance object
00092         OSInstance *osinstance;
00093         std::cout << " call nl2osil" << std::endl;
00094         try{
00095                 nl2osil->createOSInstance() ;
00096         }
00097         catch(const ErrorClass& eclass){
00098                 std::cout << eclass.errormsg << std::endl;
00099                 return 0;
00100         }
00101         std::cout << " return from  nl2osil" << std::endl;
00102         osinstance = nl2osil->osinstance;
00103         std::cout << " osinstance created" << std::endl;
00104         // turn the osinstance into osil 
00105         // not needed for a local solve
00106         // send an osinstance object in memory
00114         char *amplclient_options = NULL;
00115         char *agent_address = NULL;
00116         char *solver_option = NULL;
00117         // set solver type default to clp
00118         DefaultSolver *solverType  = NULL;      
00119         OSrLReader *osrlreader = NULL;
00120         OSrLWriter *osrlwriter;
00121         osrlwriter = new OSrLWriter();
00122         OSResult *osresult = NULL;
00123         std::string osrl = "";
00124         std::string sSolverName = "";
00125         // note that default solver is coin and default subSolver is Cbc
00126         std::string osol = "<?xml version=\"1.0\" encoding=\"UTF-8\"?> <osol xmlns=\"os.optimizationservices.org\" xmlns:xs=\"http://www.w3.org/2001/XMLSchema\" xmlns:xsi=\"http://www.w3.org/2001/XMLSchema-instance\" xsi:schemaLocation=\"os.optimizationservices.org http://www.optimizationservices.org/schemas/OSoL.xsd\"></osol>";
00127         
00128         char *num_procOption = NULL;
00129         char *num_processors = NULL;
00130         char *URL = NULL;
00131         char delims[] = " ";
00132         
00133         // get the solver set by AMPL
00134         amplclient_options = getenv("OSAmplClient_options");
00135         if( amplclient_options != NULL) cout << "HERE ARE THE AMPLCLIENT OPTIONS " <<   amplclient_options << endl;
00136         try{
00137                 if(amplclient_options == NULL ) throw ErrorClass( "a local solver was not specified in AMPL option");
00138                 else{
00139                         if( strstr(amplclient_options, "lindo") != NULL) {
00140                                 // we are requesting the Lindo solver
00141                                 bool bLindoIsPresent = false;
00142                                 #ifdef COIN_HAS_LINDO
00143                                 sSolverName = "lindo";
00144                                 bLindoIsPresent = true;
00145                                 solver_option = getenv("lindo_options");
00146                                 if(( solver_option == NULL) ||  strstr(solver_option, "service") == NULL)  solverType = new LindoSolver();
00147                                 #endif
00148                                 if(bLindoIsPresent == false) throw ErrorClass( "the Lindo solver requested is not present");
00149                         }
00150                         else{ 
00151                                 if( strstr(amplclient_options, "clp") != NULL){
00152                                         if( solver_option != NULL) cout << "HERE ARE THE Clp SOLVER OPTIONS " <<   solver_option << endl;
00153                                         sSolverName = "clp";
00154                                         solver_option = getenv("clp_options");
00155                                         if( ( solver_option == NULL) || (strstr(solver_option, "service") == NULL) ){
00156                                                 solverType = new CoinSolver();
00157                                                 solverType->sSolverName = "clp";
00158                                         }
00159                                 }
00160                                 else{
00161                                         if( strstr(amplclient_options, "cbc") != NULL){
00162                                                 sSolverName = "cbc";
00163                                                 solver_option = getenv("cbc_options");
00164                                                 if( solver_option != NULL) cout << "HERE ARE THE Cbc SOLVER OPTIONS " <<   solver_option << endl;
00165                                                 if( ( solver_option == NULL) || (strstr(solver_option, "service") == NULL)){
00166                                                         solverType = new CoinSolver();
00167                                                         solverType->sSolverName = "cbc";
00168                                                 }
00169                                         }
00170                                         else{
00171                                                 if( strstr(amplclient_options, "cplex") != NULL){
00172                                                         bool bCplexIsPresent = false;
00173                                                         #ifdef COIN_HAS_CPX
00174                                                                 bCplexIsPresent = true;
00175                                                                 sSolverName = "cplex";
00176                                                                 solver_option = getenv("cplex_options");
00177                                                                 if( solver_option != NULL) cout << "HERE ARE THE Cplex SOLVER OPTIONS " <<   solver_option << endl;
00178                                                                 if(  ( solver_option == NULL) ||  (strstr(solver_option, "service") == NULL)){
00179                                                                         solverType = new CoinSolver();
00180                                                                         solverType->sSolverName = "cplex";
00181                                                                 }
00182                                                         #endif
00183                                                                 if(bCplexIsPresent == false) throw ErrorClass( "the Cplex solver requested is not present");
00184                                                 }
00185                                                 else{
00186                                                         if( strstr(amplclient_options, "glpk") != NULL){
00187                                                                 bool bGlpkIsPresent = false;
00188                                                                 #ifdef COIN_HAS_GLPK
00189                                                                         bGlpkIsPresent = true;
00190                                                                         solverType = new CoinSolver();
00191                                                                         sSolverName = "glpk";
00192                                                                         solver_option = getenv("glpk_options");
00193                                                                         if( solver_option != NULL) cout << "HERE ARE THE Glpk SOLVER OPTIONS " <<   solver_option << endl;
00194                                                                         if( ( solver_option == NULL) || (strstr(solver_option, "service") == NULL)){
00195                                                                                 solverType = new CoinSolver();
00196                                                                                 solverType->sSolverName = "glpk";
00197                                                                         }
00198                                                                 #endif
00199                                                                 if(bGlpkIsPresent == false) throw ErrorClass( "the Glpk solver requested is not present");
00200                                                         }
00201                                                         else{
00202                                                                 if( strstr(amplclient_options, "ipopt") != NULL){
00203                                                                         bool bIpoptIsPresent = false;
00204                                                                         #ifdef COIN_HAS_IPOPT
00205                                                                                 bIpoptIsPresent = true;
00206                                                                                 sSolverName = "ipopt";
00207                                                                                 solver_option = getenv("ipopt_options");
00208                                                                                 if( solver_option != NULL) cout << "HERE ARE THE Ipopt SOLVER OPTIONS " <<   solver_option << endl;
00209                                                                                 if( ( solver_option == NULL) || (strstr(solver_option, "service") == NULL) ){
00210                                                                                         solverType = new IpoptSolver();
00211                                                                                         solverType->sSolverName = "ipopt";
00212                                                                                 }
00213                                                                         #endif
00214                                                                         if(bIpoptIsPresent == false) throw ErrorClass( "the Ipopt solver requested is not present");
00215                                                                 }
00216                                                                 else{
00217                                                                         if( strstr(amplclient_options, "symphony") != NULL){
00218                                                                                 bool bSymIsPresent = false;
00219                                                                                 #ifdef COIN_HAS_SYMPHONY
00220                                                                                         bSymIsPresent = true; 
00221                                                                                         sSolverName = "symphony";
00222                                                                                         solver_option = getenv("symphony_options");
00223                                                                                         if( solver_option != NULL) cout << "HERE ARE THE SYMPHONY SOLVER OPTIONS " <<   solver_option << endl;
00224                                                                                         // get the number of parallel parallel processors and insert into the osol
00225                                                                                         // tokenize the symphony_options string
00226                                                                                         // just test for now, make a subroutine later
00227 
00228                                                                                         //
00229                                                                                         if(solver_option != NULL){
00230                                                                                                 num_procOption = strstr(solver_option, "num_proc");
00231                                                                                                 if (num_procOption != NULL){
00232                                                                                                         // kipp -- probably should make this a subroutine in
00233                                                                                                         // case other solvers have options???
00234                                                                                                         // get the number of processors
00235                                                                                                         //move past the num_proc option name token
00236                                                                                                         num_procOption += 8;
00237                                                                                                         num_processors = strtok( num_procOption, delims );
00238                                                                                                         //
00239                                                                                                         string::size_type iStringpos;
00240                                                                                                         iStringpos = osol.find("</osol");
00241                                                                                                         std::string insertText = "<other name=\"num_proc\">";
00242                                                                                                         insertText +=  num_processors;
00243                                                                                                         insertText += "</other>";
00244                                                                                                         osol.insert(iStringpos, insertText);
00245 
00246                                                                                                 }
00247                                                                                         }
00248                                                                                         if(  ( solver_option == NULL) ||  (strstr(solver_option, "service") == NULL)){
00249                                                                                                 solverType = new CoinSolver();
00250                                                                                                 solverType->sSolverName = "symphony";
00251                                                                                         }
00252                                                                                 #endif
00253                                                                                 if(bSymIsPresent == false) throw ErrorClass( "the SYMPHONY solver requested is not present");
00254                                                                         }
00255                                                                         else{
00256                                                                                 if( strstr(amplclient_options, "dylp") != NULL){
00257                                                                                         bool bDyLPIsPresent = false;
00258                                                                                         #ifdef COIN_HAS_DYLP
00259                                                                                                 bDyLPIsPresent = true;
00260                                                                                                 sSolverName = "dylp";
00261                                                                                                 solver_option = getenv("dylp_options");
00262                                                                                                 if( solver_option != NULL) cout << "HERE ARE THE DyLP SOLVER OPTIONS " <<   solver_option << endl;
00263                                                                                                 if( ( solver_option == NULL) || (strstr(solver_option, "service") == NULL) ){
00264                                                                                                         solverType = new CoinSolver();
00265                                                                                                         solverType->sSolverName = "dylp";
00266                                                                                                 }
00267                                                                                         #endif
00268                                                                                         if(bDyLPIsPresent == false) throw ErrorClass( "the DyLP solver requested is not present");
00269                                                                                 }
00270                                                                                 else{
00271                                                                                         throw ErrorClass( "a supported solver has not been selected");
00272                                                                                 }
00273                                                                         }       
00274                                                                 } 
00275                                                         }
00276                                                 }
00277                                         }
00278                                 }
00279                         }
00280                 }
00281                 // do a local solve
00282                 if( ( solver_option == NULL) || (strstr(solver_option, "service") == NULL)  ){
00283                         solverType->osol = osol;
00284                         //std::cout << osol << std::endl;
00285                         solverType->osinstance = osinstance;
00286                         solverType->buildSolverInstance();
00287                         solverType->solve();
00288                         osrl = solverType->osrl ;
00289                         //std::cout << osrl << std::endl;
00290                 }
00291         }
00292         catch(const ErrorClass& eclass){
00293                 osresult = new OSResult();      
00294                 osresult->setGeneralMessage( eclass.errormsg);
00295                 osresult->setGeneralStatusType( "error");
00296                 osrl = osrlwriter->writeOSrL( osresult);
00297                 std::cout  << osrl << std::endl;
00298                 osrl = " ";
00299                 write_sol(const_cast<char*>(osrl.c_str()), NULL, NULL, NULL);
00300                 delete osresult;
00301                 return 0;
00302         }
00303         try{
00304                 // do the following for a remote solve
00305                 if( (solver_option != NULL) && (strstr(solver_option, "service") != NULL)){
00306                         OSSolverAgent* osagent = NULL;
00307                         OSiLWriter *osilwriter = NULL;
00308                         osilwriter = new OSiLWriter();
00309                         std::string  osil = osilwriter->writeOSiL( osinstance);
00311                         agent_address = strstr(solver_option, "service");
00312                         agent_address += 7;
00313                         URL = strtok( agent_address, delims );
00314                         std::string sURL = URL;
00316                         // we should be pointing to the start of the address
00317                         osagent = new OSSolverAgent( URL);
00318                         // if a solver option was specified put that in
00319                         string::size_type iStringpos;
00320                         iStringpos = osol.find("</osol");
00321                         //std::cout <<  solverType->sSolverName << std::endl;
00322                         std::string solverInput = "<other name=\"os_solver\">"
00323                                 + sSolverName  + "</other>";
00324                         osol.insert(iStringpos, solverInput);
00325                         cout << "Place remote synchronous call: " + sURL << endl << endl << endl;
00326                         cout << osol << endl;
00327                         osrl = osagent->solve(osil, osol);
00328                         if (osrl.size() == 0) throw ErrorClass("Nothing was returned from the server, please check service address");
00329                         delete osilwriter;
00330                         delete osagent; 
00331                 } 
00332         }
00333         catch(const ErrorClass& eclass){
00334                 osresult = new OSResult();
00335                 osresult->setGeneralMessage( eclass.errormsg);
00336                 osresult->setGeneralStatusType( "error");
00337                 osrl = osrlwriter->writeOSrL( osresult);        
00338                 write_sol(const_cast<char*>(osrl.c_str()), NULL, NULL, NULL);
00339                 delete osresult;
00340                 return 0;
00341         }
00342         try{ 
00343                 //need_nl = 0;
00344                 std::string sResultFileName = "solutionResult.osrl";
00345                 FileUtil *fileUtil;
00346                 fileUtil = new FileUtil();
00347                 fileUtil->writeFileFromString(sResultFileName, osrl);
00348                 delete fileUtil;
00349                 //cout << "WRITE THE SOLUTION BACK INTO AMPL" <<endl;
00350                 string::size_type pos1 = osrl.find( "error");
00351                 if(pos1 == std::string::npos){
00352                         std::string sReport = "model was solved";
00353                         std::cout << sReport << std::endl;
00354                         osrlreader = new OSrLReader();
00355                         osresult = osrlreader->readOSrL( osrl);
00356                         // do the following so output is not written twice
00357                         // see page 23 of hooking solver to AMPL
00358                         //need_nl = printf( sReport.c_str());
00359 
00360                         //
00361                         sReport = " ";
00362                         write_sol(  const_cast<char*>(sReport.c_str()), 
00363                                         osresult->getOptimalPrimalVariableValues( -1), 
00364                                         osresult->getOptimalDualVariableValues( -1) , NULL);
00365                         
00366                         delete osrlreader;
00367                         osrlreader = NULL;
00368                 }else{
00369                         // do the following so output is not written twice
00370                         // see page 23 of hooking solver to AMPL
00371                         std::cout  << osrl << std::endl;
00372                         osrl = " ";
00373                         //
00374                         write_sol(  const_cast<char*>(osrl.c_str()), NULL, NULL, NULL);
00375                         need_nl = 0;
00376                 }
00377                 //cout << "DONE WRITING THE SOLUTION BACK INTO AMPL" <<endl;
00378         }
00379         catch(const ErrorClass& eclass){
00380                 cout << "There was an error parsing the OSrL" << endl << eclass.errormsg << endl << endl;
00381         }
00382         if(  solverType != NULL ){
00383                 //cout << "TRY TO DELETE solverType" <<endl;
00384                 delete solverType;
00385                 //cout << "solverType JUST DELETED" <<endl;
00386                 solverType = NULL;
00387         }
00388         delete osrlwriter;
00389         //cout << "osrlwriter JUST DELETED" <<endl;
00390         osrlwriter = NULL;
00391         delete nl2osil;
00392         //cout << "nl2osil JUST DELETED" <<endl;
00393         nl2osil = NULL;
00394         ASL_free(&asl);
00395         return 0; 
00396 } // end main

Generated on Sat Mar 29 22:38:01 2008 by  doxygen 1.5.3