InProcessExampleBrowser.cpp 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432
  1. #include "InProcessExampleBrowser.h"
  2. //#define EXAMPLE_CONSOLE_ONLY
  3. #ifdef EXAMPLE_CONSOLE_ONLY
  4. #include "EmptyBrowser.h"
  5. typedef EmptyBrowser DefaultBrowser;
  6. #else
  7. #include "OpenGLExampleBrowser.h"
  8. typedef OpenGLExampleBrowser DefaultBrowser;
  9. #endif //EXAMPLE_CONSOLE_ONLY
  10. #include "Bullet3Common/b3CommandLineArgs.h"
  11. #include "../Utils/b3Clock.h"
  12. #include "ExampleEntries.h"
  13. #include "Bullet3Common/b3Scalar.h"
  14. #include "../SharedMemory/InProcessMemory.h"
  15. void ExampleBrowserThreadFunc(void* userPtr, void* lsMemory);
  16. void* ExampleBrowserMemoryFunc();
  17. void ExampleBrowserMemoryReleaseFunc(void* ptr);
  18. #include <stdio.h>
  19. //#include "BulletMultiThreaded/PlatformDefinitions.h"
  20. #include "Bullet3Common/b3Logging.h"
  21. #include "ExampleEntries.h"
  22. #include "LinearMath/btAlignedObjectArray.h"
  23. #include "EmptyExample.h"
  24. #include "../SharedMemory/PhysicsServerExample.h"
  25. #include "../SharedMemory/PhysicsServerExampleBullet2.h"
  26. #include "../SharedMemory/GraphicsServerExample.h"
  27. #include "../SharedMemory/PhysicsClientExample.h"
  28. #ifndef _WIN32
  29. #include "../MultiThreading/b3PosixThreadSupport.h"
  30. static b3ThreadSupportInterface* createExampleBrowserThreadSupport(int numThreads)
  31. {
  32. b3PosixThreadSupport::ThreadConstructionInfo constructionInfo("testThreads",
  33. ExampleBrowserThreadFunc,
  34. ExampleBrowserMemoryFunc,
  35. ExampleBrowserMemoryReleaseFunc,
  36. numThreads);
  37. b3ThreadSupportInterface* threadSupport = new b3PosixThreadSupport(constructionInfo);
  38. return threadSupport;
  39. }
  40. #elif defined(_WIN32)
  41. #include "../MultiThreading/b3Win32ThreadSupport.h"
  42. b3ThreadSupportInterface* createExampleBrowserThreadSupport(int numThreads)
  43. {
  44. b3Win32ThreadSupport::Win32ThreadConstructionInfo threadConstructionInfo("testThreads", ExampleBrowserThreadFunc, ExampleBrowserMemoryFunc, ExampleBrowserMemoryReleaseFunc, numThreads);
  45. b3Win32ThreadSupport* threadSupport = new b3Win32ThreadSupport(threadConstructionInfo);
  46. return threadSupport;
  47. }
  48. #endif
  49. class ExampleEntriesPhysicsServer : public ExampleEntries
  50. {
  51. struct ExampleEntriesInternalData2* m_data;
  52. public:
  53. ExampleEntriesPhysicsServer();
  54. virtual ~ExampleEntriesPhysicsServer();
  55. static void registerExampleEntry(int menuLevel, const char* name, const char* description, CommonExampleInterface::CreateFunc* createFunc, int option = 0);
  56. virtual void initExampleEntries();
  57. virtual void initOpenCLExampleEntries();
  58. virtual int getNumRegisteredExamples();
  59. virtual CommonExampleInterface::CreateFunc* getExampleCreateFunc(int index);
  60. virtual const char* getExampleName(int index);
  61. virtual const char* getExampleDescription(int index);
  62. virtual int getExampleOption(int index);
  63. };
  64. struct ExampleEntryPhysicsServer
  65. {
  66. int m_menuLevel;
  67. const char* m_name;
  68. const char* m_description;
  69. CommonExampleInterface::CreateFunc* m_createFunc;
  70. int m_option;
  71. ExampleEntryPhysicsServer(int menuLevel, const char* name)
  72. : m_menuLevel(menuLevel), m_name(name), m_description(0), m_createFunc(0), m_option(0)
  73. {
  74. }
  75. ExampleEntryPhysicsServer(int menuLevel, const char* name, const char* description, CommonExampleInterface::CreateFunc* createFunc, int option = 0)
  76. : m_menuLevel(menuLevel), m_name(name), m_description(description), m_createFunc(createFunc), m_option(option)
  77. {
  78. }
  79. };
  80. struct ExampleEntriesInternalData2
  81. {
  82. btAlignedObjectArray<ExampleEntryPhysicsServer> m_allExamples;
  83. };
  84. static ExampleEntryPhysicsServer gDefaultExamplesPhysicsServer[] =
  85. {
  86. ExampleEntryPhysicsServer(0, "Robotics Control"),
  87. ExampleEntryPhysicsServer(1, "Physics Server", "Create a physics server that communicates with a physics client over shared memory",
  88. PhysicsServerCreateFuncBullet2),
  89. ExampleEntryPhysicsServer(1, "Physics Server (RTC)", "Create a physics server that communicates with a physics client over shared memory. At each update, the Physics Server will continue calling 'stepSimulation' based on the real-time clock (RTC).",
  90. PhysicsServerCreateFuncBullet2, PHYSICS_SERVER_USE_RTC_CLOCK),
  91. ExampleEntryPhysicsServer(1, "Physics Server (Logging)", "Create a physics server that communicates with a physics client over shared memory. It will log all commands to a file.",
  92. PhysicsServerCreateFuncBullet2, PHYSICS_SERVER_ENABLE_COMMAND_LOGGING),
  93. ExampleEntryPhysicsServer(1, "Physics Server (Replay Log)", "Create a physics server that replay a command log from disk.",
  94. PhysicsServerCreateFuncBullet2, PHYSICS_SERVER_REPLAY_FROM_COMMAND_LOG),
  95. ExampleEntryPhysicsServer(1, "Graphics Server", "Create a graphics server", GraphicsServerCreateFuncBullet),
  96. };
  97. ExampleEntriesPhysicsServer::ExampleEntriesPhysicsServer()
  98. {
  99. m_data = new ExampleEntriesInternalData2;
  100. }
  101. ExampleEntriesPhysicsServer::~ExampleEntriesPhysicsServer()
  102. {
  103. delete m_data;
  104. }
  105. void ExampleEntriesPhysicsServer::initOpenCLExampleEntries()
  106. {
  107. }
  108. void ExampleEntriesPhysicsServer::initExampleEntries()
  109. {
  110. m_data->m_allExamples.clear();
  111. int numDefaultEntries = sizeof(gDefaultExamplesPhysicsServer) / sizeof(ExampleEntryPhysicsServer);
  112. for (int i = 0; i < numDefaultEntries; i++)
  113. {
  114. m_data->m_allExamples.push_back(gDefaultExamplesPhysicsServer[i]);
  115. }
  116. }
  117. void ExampleEntriesPhysicsServer::registerExampleEntry(int menuLevel, const char* name, const char* description, CommonExampleInterface::CreateFunc* createFunc, int option)
  118. {
  119. }
  120. int ExampleEntriesPhysicsServer::getNumRegisteredExamples()
  121. {
  122. return m_data->m_allExamples.size();
  123. }
  124. CommonExampleInterface::CreateFunc* ExampleEntriesPhysicsServer::getExampleCreateFunc(int index)
  125. {
  126. return m_data->m_allExamples[index].m_createFunc;
  127. }
  128. int ExampleEntriesPhysicsServer::getExampleOption(int index)
  129. {
  130. return m_data->m_allExamples[index].m_option;
  131. }
  132. const char* ExampleEntriesPhysicsServer::getExampleName(int index)
  133. {
  134. return m_data->m_allExamples[index].m_name;
  135. }
  136. const char* ExampleEntriesPhysicsServer::getExampleDescription(int index)
  137. {
  138. return m_data->m_allExamples[index].m_description;
  139. }
  140. struct ExampleBrowserArgs
  141. {
  142. ExampleBrowserArgs()
  143. : m_fakeWork(1), m_argc(0)
  144. {
  145. }
  146. b3CriticalSection* m_cs;
  147. float m_fakeWork;
  148. int m_argc;
  149. char** m_argv;
  150. };
  151. struct ExampleBrowserThreadLocalStorage
  152. {
  153. SharedMemoryInterface* m_sharedMem;
  154. int threadId;
  155. };
  156. enum TestExampleBrowserCommunicationEnums
  157. {
  158. eRequestTerminateExampleBrowser = 13,
  159. eExampleBrowserIsUnInitialized,
  160. eExampleBrowserIsInitialized,
  161. eExampleBrowserInitializationFailed,
  162. eExampleBrowserHasTerminated
  163. };
  164. static double gMinUpdateTimeMicroSecs = 4000.;
  165. void ExampleBrowserThreadFunc(void* userPtr, void* lsMemory)
  166. {
  167. printf("ExampleBrowserThreadFunc started\n");
  168. ExampleBrowserThreadLocalStorage* localStorage = (ExampleBrowserThreadLocalStorage*)lsMemory;
  169. ExampleBrowserArgs* args = (ExampleBrowserArgs*)userPtr;
  170. //int workLeft = true;
  171. b3CommandLineArgs args2(args->m_argc, args->m_argv);
  172. int minUpdateMs = 4000;
  173. if (args2.GetCmdLineArgument("minGraphicsUpdateTimeMs", minUpdateMs))
  174. {
  175. gMinUpdateTimeMicroSecs = minUpdateMs;
  176. }
  177. b3Clock clock;
  178. ExampleEntriesPhysicsServer examples;
  179. examples.initExampleEntries();
  180. DefaultBrowser* exampleBrowser = new DefaultBrowser(&examples);
  181. exampleBrowser->setSharedMemoryInterface(localStorage->m_sharedMem);
  182. bool init = exampleBrowser->init(args->m_argc, args->m_argv);
  183. clock.reset();
  184. if (init)
  185. {
  186. args->m_cs->lock();
  187. args->m_cs->setSharedParam(0, eExampleBrowserIsInitialized);
  188. args->m_cs->unlock();
  189. do
  190. {
  191. clock.usleep(0);
  192. //B3_PROFILE("ExampleBrowserThreadFunc");
  193. float deltaTimeInSeconds = clock.getTimeMicroseconds() / 1000000.f;
  194. {
  195. if (deltaTimeInSeconds > 0.1)
  196. {
  197. deltaTimeInSeconds = 0.1;
  198. }
  199. if (deltaTimeInSeconds < (gMinUpdateTimeMicroSecs / 1e6))
  200. {
  201. //B3_PROFILE("clock.usleep");
  202. exampleBrowser->updateGraphics();
  203. }
  204. else
  205. {
  206. //B3_PROFILE("exampleBrowser->update");
  207. clock.reset();
  208. exampleBrowser->updateGraphics();
  209. exampleBrowser->update(deltaTimeInSeconds);
  210. }
  211. }
  212. } while (!exampleBrowser->requestedExit() && (args->m_cs->getSharedParam(0) != eRequestTerminateExampleBrowser));
  213. }
  214. else
  215. {
  216. args->m_cs->lock();
  217. args->m_cs->setSharedParam(0, eExampleBrowserInitializationFailed);
  218. args->m_cs->unlock();
  219. }
  220. delete exampleBrowser;
  221. args->m_cs->lock();
  222. args->m_cs->setSharedParam(0, eExampleBrowserHasTerminated);
  223. args->m_cs->unlock();
  224. printf("finished\n");
  225. //do nothing
  226. }
  227. void* ExampleBrowserMemoryFunc()
  228. {
  229. //don't create local store memory, just return 0
  230. return new ExampleBrowserThreadLocalStorage;
  231. }
  232. void ExampleBrowserMemoryReleaseFunc(void* ptr)
  233. {
  234. ExampleBrowserThreadLocalStorage* p = (ExampleBrowserThreadLocalStorage*)ptr;
  235. delete p;
  236. }
  237. struct btInProcessExampleBrowserInternalData
  238. {
  239. ExampleBrowserArgs m_args;
  240. b3ThreadSupportInterface* m_threadSupport;
  241. SharedMemoryInterface* m_sharedMem;
  242. };
  243. btInProcessExampleBrowserInternalData* btCreateInProcessExampleBrowser(int argc, char** argv2, bool useInProcessMemory)
  244. {
  245. btInProcessExampleBrowserInternalData* data = new btInProcessExampleBrowserInternalData;
  246. data->m_sharedMem = useInProcessMemory ? new InProcessMemory : 0;
  247. int numThreads = 1;
  248. int i;
  249. data->m_threadSupport = createExampleBrowserThreadSupport(numThreads);
  250. printf("argc=%d\n", argc);
  251. for (i = 0; i < argc; i++)
  252. {
  253. printf("argv[%d] = %s\n", i, argv2[i]);
  254. }
  255. for (i = 0; i < data->m_threadSupport->getNumTasks(); i++)
  256. {
  257. ExampleBrowserThreadLocalStorage* storage = (ExampleBrowserThreadLocalStorage*)data->m_threadSupport->getThreadLocalMemory(i);
  258. b3Assert(storage);
  259. storage->threadId = i;
  260. storage->m_sharedMem = data->m_sharedMem;
  261. }
  262. data->m_args.m_cs = data->m_threadSupport->createCriticalSection();
  263. data->m_args.m_cs->setSharedParam(0, eExampleBrowserIsUnInitialized);
  264. data->m_args.m_argc = argc;
  265. data->m_args.m_argv = argv2;
  266. for (i = 0; i < numThreads; i++)
  267. {
  268. data->m_threadSupport->runTask(B3_THREAD_SCHEDULE_TASK, (void*)&data->m_args, i);
  269. }
  270. while (data->m_args.m_cs->getSharedParam(0) == eExampleBrowserIsUnInitialized)
  271. {
  272. b3Clock::usleep(1000);
  273. }
  274. return data;
  275. }
  276. bool btIsExampleBrowserTerminated(btInProcessExampleBrowserInternalData* data)
  277. {
  278. return (data->m_args.m_cs->getSharedParam(0) == eExampleBrowserHasTerminated);
  279. }
  280. SharedMemoryInterface* btGetSharedMemoryInterface(btInProcessExampleBrowserInternalData* data)
  281. {
  282. return data->m_sharedMem;
  283. }
  284. void btShutDownExampleBrowser(btInProcessExampleBrowserInternalData* data)
  285. {
  286. int numActiveThreads = 1;
  287. data->m_args.m_cs->lock();
  288. data->m_args.m_cs->setSharedParam(0, eRequestTerminateExampleBrowser);
  289. data->m_args.m_cs->unlock();
  290. while (numActiveThreads)
  291. {
  292. int arg0, arg1;
  293. if (data->m_threadSupport->isTaskCompleted(&arg0, &arg1, 0))
  294. {
  295. numActiveThreads--;
  296. printf("numActiveThreads = %d\n", numActiveThreads);
  297. }
  298. else
  299. {
  300. // printf("polling..");
  301. b3Clock::usleep(0);
  302. }
  303. };
  304. printf("btShutDownExampleBrowser stopping threads\n");
  305. data->m_threadSupport->deleteCriticalSection(data->m_args.m_cs);
  306. delete data->m_threadSupport;
  307. delete data->m_sharedMem;
  308. delete data;
  309. }
  310. struct btInProcessExampleBrowserMainThreadInternalData
  311. {
  312. ExampleEntriesPhysicsServer m_examples;
  313. DefaultBrowser* m_exampleBrowser;
  314. SharedMemoryInterface* m_sharedMem;
  315. b3Clock m_clock;
  316. };
  317. btInProcessExampleBrowserMainThreadInternalData* btCreateInProcessExampleBrowserMainThread(int argc, char** argv, bool useInProcessMemory)
  318. {
  319. btInProcessExampleBrowserMainThreadInternalData* data = new btInProcessExampleBrowserMainThreadInternalData;
  320. data->m_examples.initExampleEntries();
  321. data->m_exampleBrowser = new DefaultBrowser(&data->m_examples);
  322. data->m_sharedMem = useInProcessMemory ? new InProcessMemory : 0;
  323. data->m_exampleBrowser->setSharedMemoryInterface(data->m_sharedMem);
  324. bool init;
  325. init = data->m_exampleBrowser->init(argc, argv);
  326. data->m_clock.reset();
  327. return data;
  328. }
  329. bool btIsExampleBrowserMainThreadTerminated(btInProcessExampleBrowserMainThreadInternalData* data)
  330. {
  331. return data->m_exampleBrowser->requestedExit();
  332. }
  333. void btUpdateInProcessExampleBrowserMainThread(btInProcessExampleBrowserMainThreadInternalData* data)
  334. {
  335. float deltaTimeInSeconds = data->m_clock.getTimeMicroseconds() / 1000000.f;
  336. data->m_clock.reset();
  337. data->m_exampleBrowser->updateGraphics();
  338. data->m_exampleBrowser->update(deltaTimeInSeconds);
  339. }
  340. void btShutDownExampleBrowserMainThread(btInProcessExampleBrowserMainThreadInternalData* data)
  341. {
  342. data->m_exampleBrowser->setSharedMemoryInterface(0);
  343. delete data->m_exampleBrowser;
  344. delete data;
  345. }
  346. class SharedMemoryInterface* btGetSharedMemoryInterfaceMainThread(btInProcessExampleBrowserMainThreadInternalData* data)
  347. {
  348. return data->m_sharedMem;
  349. }