c++与python通信
步骤
0.c++编译带有使用共享内存函数的动态链接库
1.c++开内存,读内存
2.python写内存
注:二者的内存同一地址。
程序
#ifndef __SHRMM_HPP_
#define __SHRMM_HPP_
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <sys/types.h>
#include <sys/ipc.h>
#include <sys/shm.h>
class TestLib
{
public:
TestLib() {addr = NULL; shmid = 0; size = 0;};
int open_shm(int share_memory_key, int share_feature);
int close_shm();
void* get_address();
int get_maxsize();
private:
int shmid = 0;
int size = 0;
void* addr = NULL;
};
#endif // __SHRMM_HPP_
#include "shrmm.hpp"
#include "iostream"
int TestLib::open_shm(int share_memory_key, int share_memory_size)
{
int id;
if (share_memory_key <= 0) return 0;
id = shmget(share_memory_key, share_memory_size, 0666 | IPC_CREAT);
if (id == -1) return 0;
shmid = id;
size = share_memory_size;
addr = shmat(shmid, (void *)0, 0);
return 1;
}
/**
* @brief free the share memory
* <long-description>
*
* @param
* @return <ReturnValue>
*/
int TestLib:: close_shm()
{
int rtn;
rtn = shmdt(addr);
return rtn;
}
/**
* @brief get address of share memory
* <long-description>
*
* @param
* @return <ReturnValue>
*/
void* TestLib::get_address()
{
if (addr == NULL) return NULL;
return (void*) addr;
}
/**
* @brief get the size of created share memory
* <long-description>
*
* @param
* @return <ReturnValue>
*/
int TestLib::get_maxsize()
{
return size;
}
extern "C" {
TestLib obj;
int open_shm(int share_memory_key, int share_memory_size) {
int id = obj.open_shm(share_memory_key, share_memory_size);
return id;
}
int close_shm() {
int rtn = obj.close_shm();
return rtn;
}
void * get_address() {
void * add1;
add1 = obj.get_address();
return add1;
}
}
cmake_minimum_required(VERSION 3.1.0)
project (lib)
set (CMAKE_CXX_STANDARD 14)
set(CMAKE_EXPORT_COMPILE_COMMANDS 1)
set(CMAKE_BUILD_TYPE "Release")
set(BOOST_LIBS date_time system)
include_directories("../include/"
)
add_library(m_sharmMem SHARED ../shrmm.cpp)
set(libso m_sharmMem )
set(includeFile ../include/shrmm.hpp )
target_link_libraries(${libso})
#ifndef _MAIN_H
#define _MAIN_H
#include "main.h"
#include <iostream>
#include "shrmm.hpp"
using namespace std;
int initial_memory();
typedef struct Features {
int Image_X;
int Image_Y;
float Image_Z;
int Class_Id;
}Features;
TestLib m_sh_cmd_features;
Features *pStatus_feature;
// share_memory m_sh_cmd_feature;
#endif
#include "main.h"
#include <iostream>
#include "stdio.h"
using namespace std;
int main(int argc, char *argv[]) {
initial_memory();
pStatus_feature->Class_Id = 0;
pStatus_feature->Image_X = 1;
pStatus_feature->Image_Y = 2;
pStatus_feature->Image_Z = 3;
while(1) {
cout<< "the image features xxxxxxx:"<< pStatus_feature->Image_X<< endl;
cout<< "the image features yyyyyyy:"<< pStatus_feature->Image_Y<< endl;
cout<< "the image features zzzzzzz:"<< pStatus_feature->Image_Z<< endl;
cout<< "the image features iiiiiii:"<< pStatus_feature->Class_Id<< endl;
}
cout << "exit " << endl;
return 0;
}
// open the share memory
int initial_memory() {
int i = shmget(4600, 1024, 0666|IPC_CREAT);;
if(i == 0) {
cout<< "error"<< endl;
return 0;
}
void* addr = NULL;
addr = shmat(i, (void *)0, 0);
pStatus_feature = (Features*)addr;
memset(pStatus_feature, 0, sizeof(Features));
return 1;
}
cmake_minimum_required(VERSION 2.8)
project(calibControl)
include(CheckCXXCompilerFlag)
CHECK_CXX_COMPILER_FLAG("-std=c++11" COMPILER_SUPPORTS_CXX11)
CHECK_CXX_COMPILER_FLAG("-std=c++0x" COMPILER_SUPPORTS_CXX0X)
# 使用变量设置编译标志
if(COMPILER_SUPPORTS_CXX11)
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++11")
elseif(COMPILER_SUPPORTS_CXX0X)
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++0x")
else()
message(STATUS "The compiler ${CMAKE_CXX_COMPILER} has no C++11 support. Please use a different C++ compiler.")
endif()
SET(CMAKE_BUILD_TYPE "Release")
SET(CMAKE_CXX_FLAGS_DEBUG "$ENV{CXXFLAGS} -O0 -Wall -g -ggdb")
SET(CMAKE_CXX_FLAGS_RELEASE "$ENV{CXXFLAGS} -O3 -Wall")
include_directories("./include/")
include_directories("./")
aux_source_directory(./src SRC_FILES)
set(SRC_LIST ${SRC_FILES})
#add_executable(memoryTest main.cpp ./src/shrmm.cpp)
add_executable(memoryTest main.cpp ${SRC_LIST})
target_link_libraries(memoryTest ${PROJECT_SOURCE_DIR}/lib/libm_sharmMem.so)
import os
import ctypes
from ctypes import *
import sys
import struct
#import posix_ipc
from configparser import ConfigParser
# def initShm():
#ll = ctypes.cdll.LoadLibrary
var = []
lib = cdll.LoadLibrary('./lib/libm_sharmMem.so')
class image_show_struct (ctypes.Structure):
_fields_ = [("image_x", ctypes.c_int),
("image_y", ctypes.c_int),
("image_z", ctypes.c_float),
("class_id", ctypes.c_int)]
#config = ConfigParser()
#config.read("./config.ini")
#SHM_KEY = config.getint("shareM", "id")
SHM_KEY = 4600
SHM_SIZE = 1024
# this part is used to define shmget and shmat in python
shmget = lib.shmget
shmget.argtypes = [c_int, c_size_t, c_int]
shmget.restype = c_int
shmat = lib.shmat
shmat.argtypes = [c_int, POINTER(c_void_p), c_int]
shmat.restype = POINTER(image_show_struct)
shmid = shmget(SHM_KEY, SHM_SIZE, 0o666)
print(shmid)
if shmid < 0:
print ("System not infected")
else:
addr = shmat(shmid, None, 0)
print(addr)
# use the parameters in C++
for x in range(1, 10):
addr.contents.image_x=x
addr.contents.image_y=2*x
addr.contents.image_z=3*x
var = [addr.contents.image_x, addr.contents.image_y, addr.contents.image_z]
print(var)
addr.contents.class_id = 4*x
cls_id = addr.contents.class_id
print(cls_id)
if id == 0:
print("error")
else:
print("ok")
print("end")