さまざまなプロセスが管理対象共有メモリに格納されたデータにアクセスできるプログラムを作成しようとしています。私は仕事を達成するためにブーストを利用しています。私は3つのファイル、shared_memory.h、shared_memory.cc、main.ccを持っています。ブースト管理された共有メモリsegfault
shared_memory.h
#ifndef __SHARED_ITN__
#define __SHARED_ITN__
#include <fst/fstlib.h>
#include <boost/interprocess/managed_shared_memory.hpp>
#include <boost/interprocess/allocators/allocator.hpp>
#include <boost/interprocess/containers/vector.hpp>
enum TokenType { SYMBOL = 1, BYTE = 2, UTF8 = 3 };
using namespace boost::interprocess;
typedef fst::VectorFst<fst::StdArc> Transducer;
typedef allocator<Transducer, managed_shared_memory::segment_manager> shmMyFstAllocator;
typedef boost::interprocess::vector<Transducer, shmMyFstAllocator> shmMyFst;
class SharedItn {
public:
SharedItn();
SharedItn(std::vector<string> model_path);
bool Read(std::vector<string> model_path, string input_str, string &output_str);
void Remove();
virtual ~SharedItn();
private:
static const string SHM_OBJ_IDENTIFIER;
static const int SHM_OBJ_SIZE;
shmMyFst* myFstPtr;
};
#endif
対応するC++コード、shared_memory.ccは次のとおりです。
shared_memory.cc
#include "shared_memory.h"
#include <cstdlib>
#include <cstring>
#include <vector>
using namespace fst;
typedef VectorFst<StdArc> Transducer;
typedef StringCompiler<StdArc> Compiler;
const string SharedItn::SHM_OBJ_IDENTIFIER = "SHARED_ITN_MODULES";
const int SharedItn::SHM_OBJ_SIZE = 104857600;
SharedItn::SharedItn() {
}
SharedItn::SharedItn(std::vector<string> model_path) {
try {
// Create managed shared memory object
shared_memory_object::remove(SHM_OBJ_IDENTIFIER.c_str());
managed_shared_memory segment(create_only, SHM_OBJ_IDENTIFIER.c_str(), SHM_OBJ_SIZE);
// Construct fst model within the shared memory object
shmMyFstAllocator alloc_inst(segment.get_segment_manager());
myFstPtr = segment.construct<shmMyFst>(model_path[0].c_str())(alloc_inst);
// Insert the loaded fst model into shared memory
Transducer* tmp_model_fst = Transducer::Read(model_path[0]);
myFstPtr->push_back(*tmp_model_fst);
} catch (interprocess_exception& e) {
std::cout << e.what() << std::endl;
}
}
SharedItn::~SharedItn() {}
bool SharedItn::Read(std::vector<string> model_path, string input_str, string& output_str) {
Transducer* transTmp;
shmMyFst* tmp;
try {
managed_shared_memory segment(open_only, SHM_OBJ_IDENTIFIER.c_str());
tmp = segment.find<shmMyFst>(model_path[0].c_str()).first;
for(int i = 0; i < tmp->size(); i++)
transTmp = tmp->at(i).Copy(true);
} catch (interprocess_exception& e) {
std::cout << e.what() << std::endl;
return false;
}
return true;
}
void SharedItn::Remove() {
try {
shared_memory_object::remove(SHM_OBJ_IDENTIFIER.c_str());
} catch(interprocess_exception& e) {
std::cout << e.what() << std::endl;
}
}
そして最後に、サーバ/クライアント・プロセスが作成されmain.ccファイル。
main.cc
#include "shared_memory.h"
int main(int argc, char* argv[]) {
if(argc != 2) {
std::cout << "Must provide either 'server' or 'client' as input." << std::endl;
return -1;
} else {
std::vector<string> file_path;
std::string file = "rule_PRE_PROC.fst";
file_path.push_back(file);
string input_str = "";
string result_str;
if(std::string(argv[1]) == "server") {
SharedItn loader(file_path);
while(1) {
std::cout << "Input test string: " << std::endl;
getline(std::cin, input_str);
if(input_str.compare("quit") == 0) {
loader.Remove();
std::cout << "Terminating." << std::endl;
break;
}
loader.Read(file_path, input_str, result_str);
std::cout << "RESULT: " << result_str << std::endl;
}
} else if(std::string(argv[1]) == "client") {
SharedItn loader;
while(1) {
std::cout << "Input test string: " << std::endl;
getline(std::cin, input_str);
if(input_str.compare("quit") == 0) {
loader.Remove();
std::cout << "Terminating." << std::endl;
break;
}
loader.Read(file_path, input_str, result_str);
std::cout << "RESULT: " << result_str << std::endl;
}
}
}
}
私はサーバモードとして、プログラムを実行すると、すべてが正常に動作します。しかし、実行中のサーバー・プロセスがあり、追加のクライアント・プロセスを作成すると、共有メモリー内で構築されたオブジェクトを見つけようとするときにsegfaultsが発生します。具体的には、SharedItn::Read
関数内のtransTmp = tmp->at(i).Copy(true);
というコードでsegfaultが発生します。
クライアントから呼び出されたfindメソッドが正しく機能していないことを推測します。しかし、私は問題が何であるか把握することはできません。どんな助けでも大歓迎です。
ご覧のとおり、誰もこの大量のコードを掘り下げようとしていませんでした。次回MCVEで試してみてください。 –
@AlBundyトラフィックの少ないタグでは7時間と非常に短いです。コードはSSCCE – sehe