main.cpp 3.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121
  1. /*=============================================================================
  2. Copyright (c) 2001-2011 Joel de Guzman
  3. Distributed under the Boost Software License, Version 1.0. (See accompanying
  4. file LICENSE_1_0.txt or copy at http://www.boost.org/LICENSE_1_0.txt)
  5. =============================================================================*/
  6. ///////////////////////////////////////////////////////////////////////////////
  7. //
  8. // Not a calculator anymore, right? :-)
  9. //
  10. // [ JDG April 10, 2007 ] spirit2
  11. // [ JDG February 18, 2011 ] Pure attributes. No semantic actions.
  12. //
  13. ///////////////////////////////////////////////////////////////////////////////
  14. #include "function.hpp"
  15. #include "skipper.hpp"
  16. #include "vm.hpp"
  17. #include "compiler.hpp"
  18. #include <boost/lexical_cast.hpp>
  19. #include <fstream>
  20. ///////////////////////////////////////////////////////////////////////////////
  21. // Main program
  22. ///////////////////////////////////////////////////////////////////////////////
  23. int main(int argc, char **argv)
  24. {
  25. char const* filename;
  26. if (argc > 1)
  27. {
  28. filename = argv[1];
  29. }
  30. else
  31. {
  32. std::cerr << "Error: No input file provided." << std::endl;
  33. return 1;
  34. }
  35. std::ifstream in(filename, std::ios_base::in);
  36. if (!in)
  37. {
  38. std::cerr << "Error: Could not open input file: "
  39. << filename << std::endl;
  40. return 1;
  41. }
  42. std::string source_code; // We will read the contents here.
  43. in.unsetf(std::ios::skipws); // No white space skipping!
  44. std::copy(
  45. std::istream_iterator<char>(in),
  46. std::istream_iterator<char>(),
  47. std::back_inserter(source_code));
  48. typedef std::string::const_iterator iterator_type;
  49. iterator_type iter = source_code.begin();
  50. iterator_type end = source_code.end();
  51. client::vmachine vm; // Our virtual machine
  52. client::ast::function_list ast; // Our AST
  53. client::error_handler<iterator_type>
  54. error_handler(iter, end); // Our error handler
  55. client::parser::function<iterator_type>
  56. function(error_handler); // Our parser
  57. client::parser::skipper<iterator_type>
  58. skipper; // Our skipper
  59. client::code_gen::compiler
  60. compiler(error_handler); // Our compiler
  61. bool success = phrase_parse(iter, end, +function, skipper, ast);
  62. std::cout << "-------------------------\n";
  63. if (success && iter == end)
  64. {
  65. if (compiler(ast))
  66. {
  67. boost::shared_ptr<client::code_gen::function>
  68. p = compiler.find_function("main");
  69. if (!p)
  70. return 1;
  71. int nargs = argc-2;
  72. if (p->nargs() != nargs)
  73. {
  74. std::cerr << "Error: main function requires " << p->nargs() << " arguments." << std::endl;
  75. std::cerr << nargs << "supplied." << std::endl;
  76. return 1;
  77. }
  78. std::cout << "Success\n";
  79. std::cout << "-------------------------\n";
  80. std::cout << "Assembler----------------\n\n";
  81. compiler.print_assembler();
  82. // Push the arguments into our stack
  83. for (int i = 0; i < nargs; ++i)
  84. vm.get_stack()[i] = boost::lexical_cast<int>(argv[i+2]);
  85. // Call the interpreter
  86. int r = vm.execute(compiler.get_code());
  87. std::cout << "-------------------------\n";
  88. std::cout << "Result: " << r << std::endl;
  89. std::cout << "-------------------------\n\n";
  90. }
  91. else
  92. {
  93. std::cout << "Compile failure\n";
  94. }
  95. }
  96. else
  97. {
  98. std::cout << "Parse failure\n";
  99. }
  100. return 0;
  101. }