Molecular Modeling Software
リビジョン | d1da522ab22f1ba5a4316ab13b5ca9574f682826 (tree) |
---|---|
日時 | 2010-02-04 01:02:23 |
作者 | toshinagata1964 <toshinagata1964@a2be...> |
コミッター | toshinagata1964 |
The multithread handling for MM/MD is improved.
git-svn-id: svn+ssh://svn.sourceforge.jp/svnroot/molby/trunk@6 a2be9bc6-48de-4e38-9406-05402d4bc13c
@@ -1588,6 +1588,18 @@ md_prepare(MDArena *arena, int check_only) | ||
1588 | 1588 | arena->pair_forces = NULL; |
1589 | 1589 | } |
1590 | 1590 | |
1591 | + /* Allocate ring buffer */ | |
1592 | + if (arena->ring != NULL) | |
1593 | + free(arena->ring); | |
1594 | + arena->nringframes = 2000 / mol->natoms; | |
1595 | + if (arena->nringframes == 0) | |
1596 | + arena->nringframes = 1; | |
1597 | + arena->ring = (Vector *)malloc(sizeof(Vector) * mol->natoms * arena->nringframes); | |
1598 | + if (arena->ring == NULL) | |
1599 | + md_panic(arena, ERROR_out_of_memory); | |
1600 | + arena->ring_next = 0; | |
1601 | + arena->ring_count = 0; | |
1602 | + | |
1591 | 1603 | /* Initialize temperature statistics */ |
1592 | 1604 | arena->sum_temperature = 0.0; |
1593 | 1605 | arena->nsum_temperature = 0; |
@@ -3016,6 +3028,8 @@ md_arena_release(MDArena *arena) | ||
3016 | 3028 | free(arena->old_pos); |
3017 | 3029 | if (arena->graphite != NULL) |
3018 | 3030 | graphite_release(arena->graphite); |
3031 | + if (arena->ring != NULL) | |
3032 | + free(arena->ring); | |
3019 | 3033 | free(arena); |
3020 | 3034 | } |
3021 | 3035 |
@@ -267,6 +267,11 @@ typedef struct MDArena { | ||
267 | 267 | |
268 | 268 | Int natoms_uniq; /* Number of symmetry-unique atoms */ |
269 | 269 | |
270 | + Vector *ring; /* Ring buffer for sending coordinates between threads */ | |
271 | + Int nringframes; /* Number of frames in the ring buffer (2000 / natoms) */ | |
272 | + Int ring_next; /* Next frame index to store data */ | |
273 | + Int ring_count; /* Number of frames currently in the ring buffer */ | |
274 | + | |
270 | 275 | /* Parameters are copied from mol->par and gBuiltinParameters for each call to md_prepare() */ |
271 | 276 | Parameter *par; |
272 | 277 |
@@ -8,3 +8,7 @@ make -f Makefile_at でビルド。 | ||
8 | 8 | なお、Mac 用の gfortran は http://r.research.att.com/tools/ にあるやつがいい。hpc.sourceforge.net のやつはいろいろと使い方が複雑。 |
9 | 9 | OS 10.4 用のユニバーサルバイナリは、export ISYSROOT='-isysroot /Developer/SDKs/MacOSX10.4u.sdk -mmacosx-version-min=10.4 -arch ppc -arch i386' としたあと make -f Makefile_at とすると作ることができる。MacBook 上でビルドして、PowerPC の 10.4 に持って行っても実行できたので、たぶん大丈夫じゃないかと。 |
10 | 10 | 原子タイプのアサインだけなら、antechamber を -c オプション無しで走らせればいいんだな。気がついてなかった。(どれぐらい使えるのかは不明だが。) |
11 | + | |
12 | +2010.2.2. | |
13 | + MD/Minimize のサブスレッドの処理を整理(よくフリーズしていたので)。 | |
14 | + サブスレッドから MM/MD をしているときは、指定したステップが終わるごとにリングバッファに座標データをためこみ、メインスレッドにイベントを投げる。メインスレッドはイベントを捕まえて、リングバッファから座標データを読み込んで、フレームを作成する。サブスレッドから Molecule を直接触ることがなくなったので、少しは安定すると期待しよう。また、ドキュメントを閉じるときにサブスレッドが走っている時は、エラーメッセージを出して閉じるのを拒否するようにした。 |
@@ -64,6 +64,7 @@ const wxEventType MyDocumentEvent = wxNewEventType(); | ||
64 | 64 | BEGIN_EVENT_TABLE(MyDocument, wxDocument) |
65 | 65 | EVT_COMMAND(MyDocumentEvent_willNeedCleanUndoStack, MyDocumentEvent, MyDocument::OnNeedCleanUndoStack) |
66 | 66 | EVT_COMMAND(MyDocumentEvent_documentModified, MyDocumentEvent, MyDocument::OnDocumentModified) |
67 | + EVT_COMMAND(MyDocumentEvent_insertFrameFromMD, MyDocumentEvent, MyDocument::OnInsertFrameFromMD) | |
67 | 68 | EVT_COMMAND(MyDocumentEvent_updateDisplay, MyDocumentEvent, MyDocument::OnUpdateDisplay) |
68 | 69 | EVT_COMMAND(MyDocumentEvent_threadTerminated, MyDocumentEvent, MyDocument::OnSubThreadTerminated) |
69 | 70 | EVT_MENU(myMenuID_Import, MyDocument::OnImport) |
@@ -396,6 +397,20 @@ MyDocument::CleanUndoStack(bool shouldRegister) | ||
396 | 397 | currentCommand = NULL; |
397 | 398 | } |
398 | 399 | |
400 | +bool | |
401 | +MyDocument::Close() | |
402 | +{ | |
403 | + if (mol != NULL && mol->mutex != NULL) { | |
404 | + const char *msg; | |
405 | + if (subThreadKind == 1) | |
406 | + msg = "MM/MD"; | |
407 | + else msg = "Some background process"; | |
408 | + MyAppCallback_errorMessageBox("%s is running: please stop it before closing", msg); | |
409 | + return false; | |
410 | + } | |
411 | + return true; | |
412 | +} | |
413 | + | |
399 | 414 | void |
400 | 415 | MyDocument::OnNeedCleanUndoStack(wxCommandEvent& event) |
401 | 416 | { |
@@ -650,8 +665,7 @@ sDoMolecularDynamics(void *argptr, int argnum) | ||
650 | 665 | mol->arena->end_step = mol->arena->start_step; |
651 | 666 | md_main(mol->arena, minimize); |
652 | 667 | } else if (count > 0) { |
653 | - IntGroup *ig; | |
654 | - wxCommandEvent displayEvent(MyDocumentEvent, MyDocumentEvent_updateDisplay); | |
668 | + wxCommandEvent insertFrameEvent(MyDocumentEvent, MyDocumentEvent_insertFrameFromMD); | |
655 | 669 | for (i = 0; i < count; i++) { |
656 | 670 | |
657 | 671 | mol->arena->end_step = mol->arena->start_step + mol->arena->coord_output_freq; |
@@ -662,17 +676,30 @@ sDoMolecularDynamics(void *argptr, int argnum) | ||
662 | 676 | r = -1; |
663 | 677 | else { |
664 | 678 | |
665 | - /* Create a new frame and copy the new coordinates */ | |
679 | + /* Copy the coordinate to the ring buffer */ | |
680 | + Vector *rp = mol->arena->ring + mol->natoms * mol->arena->ring_next; | |
681 | + Int j; | |
682 | + Atom *ap; | |
666 | 683 | MoleculeLock(mol); |
684 | + for (j = 0, ap = mol->arena->mol->atoms; j < mol->natoms; j++, ap = ATOM_NEXT(ap)) { | |
685 | + rp[j] = ap->r; | |
686 | + } | |
687 | + mol->arena->ring_next = (mol->arena->ring_next + 1) % mol->arena->nringframes; | |
688 | + if (mol->arena->ring_count < mol->arena->nringframes) | |
689 | + mol->arena->ring_count++; | |
690 | + MoleculeUnlock(mol); | |
691 | + | |
692 | + /* Create a new frame and copy the new coordinates */ | |
693 | + /* MoleculeLock(mol); | |
667 | 694 | ig = IntGroupNewWithPoints(MoleculeGetNumberOfFrames(mol), 1, -1); |
668 | 695 | MolActionCreateAndPerform(mol, gMolActionInsertFrames, ig, 0, NULL); |
669 | 696 | IntGroupRelease(ig); |
670 | 697 | md_copy_coordinates_from_internal(mol->arena); |
671 | - MoleculeUnlock(mol); | |
698 | + MoleculeUnlock(mol); */ | |
672 | 699 | |
673 | 700 | if (minimize && mol->arena->minimize_complete) |
674 | 701 | break; |
675 | - wxPostEvent(doc, displayEvent); | |
702 | + wxPostEvent(doc, insertFrameEvent); | |
676 | 703 | } |
677 | 704 | } |
678 | 705 | if (r != 0) |
@@ -727,6 +754,33 @@ MyDocument::OnStopMDRun(wxCommandEvent &event) | ||
727 | 754 | } |
728 | 755 | |
729 | 756 | void |
757 | +MyDocument::OnInsertFrameFromMD(wxCommandEvent &event) | |
758 | +{ | |
759 | + Int i, j, n, old_nframes; | |
760 | + Atom *ap; | |
761 | + | |
762 | + /* Create new frame(s) and copy the new coordinates from the ring buffer */ | |
763 | + MoleculeLock(mol); | |
764 | + n = mol->arena->ring_count; | |
765 | + if (n > 0) { | |
766 | + IntGroup *ig; | |
767 | + Vector *rp; | |
768 | + old_nframes = MoleculeGetNumberOfFrames(mol); | |
769 | + ig = IntGroupNewWithPoints(old_nframes, n, -1); | |
770 | + MolActionCreateAndPerform(mol, gMolActionInsertFrames, ig, 0, NULL); | |
771 | + IntGroupRelease(ig); | |
772 | + for (i = 0; i < n; i++) { | |
773 | + MoleculeSelectFrame(mol, old_nframes + i, 1); | |
774 | + rp = mol->arena->ring + ((mol->arena->ring_next + mol->arena->nringframes - n + i) % mol->arena->nringframes) * mol->natoms; | |
775 | + for (j = 0, ap = mol->atoms; j < mol->natoms; j++, ap = ATOM_NEXT(ap)) | |
776 | + ap->r = rp[j]; | |
777 | + } | |
778 | + mol->arena->ring_count = 0; | |
779 | + } | |
780 | + MoleculeUnlock(mol); | |
781 | +} | |
782 | + | |
783 | +void | |
730 | 784 | MyDocument::OnUpdateDisplay(wxCommandEvent &event) |
731 | 785 | { |
732 | 786 | MainView *mview = GetMainView(); |
@@ -30,6 +30,7 @@ enum { | ||
30 | 30 | MyDocumentEvent_documentModified, |
31 | 31 | MyDocumentEvent_scriptMenuModified, |
32 | 32 | MyDocumentEvent_updateDisplay, |
33 | + MyDocumentEvent_insertFrameFromMD, | |
33 | 34 | MyDocumentEvent_threadTerminated |
34 | 35 | }; |
35 | 36 |
@@ -70,6 +71,8 @@ public: | ||
70 | 71 | void UpdateModifyFlag(); |
71 | 72 | void BeginUndoGrouping(); |
72 | 73 | void EndUndoGrouping(); |
74 | + | |
75 | + virtual bool Close(); | |
73 | 76 | |
74 | 77 | void OnNeedCleanUndoStack(wxCommandEvent& event); |
75 | 78 |
@@ -115,6 +118,7 @@ public: | ||
115 | 118 | void OnCreateGamessInput(wxCommandEvent &event); |
116 | 119 | void OnCreateMOCube(wxCommandEvent &event); |
117 | 120 | |
121 | + void OnInsertFrameFromMD(wxCommandEvent &event); | |
118 | 122 | void OnUpdateDisplay(wxCommandEvent &event); |
119 | 123 | void OnSubThreadTerminated(wxCommandEvent &event); |
120 | 124 |