* Copyright (c) 2025 Huawei Technologies Co., Ltd.
* This program is free software, you can redistribute it and/or modify it under the terms and conditions of
* CANN Open Software License Agreement Version 2.0 (the "License").
* Please refer to the License for details. You may not use this file except in compliance with the License.
* THIS SOFTWARE IS PROVIDED ON AN "AS IS" BASIS, WITHOUT WARRANTIES OF ANY KIND, EITHER EXPRESS OR IMPLIED,
* INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT, MERCHANTABILITY, OR FITNESS FOR A PARTICULAR PURPOSE.
* See LICENSE in the root of the software repository for the full text of the License.
*/
#include "share_mem.h"
#include <sys/ipc.h>
#include <sys/shm.h>
#include "log_print.h"
#define MSG_MEMORY_KEY 0x474f4c46
* @brief: get shared memory segment
* @param [in]key: share memory key
* @param [in]msgFlag: message flag
* @return: failed:-1:;succeed:share memory key
*/
STATIC INLINE int32_t ToolShmGet(key_t key, size_t size, int32_t shmflg)
{
return shmget(key, size, shmflg);
}
* @brief: shared memory attach operation
* @param [in]shmid:identifier ID
* @param [in]shmaddr:Points to the desired address of the shared memory segment.
* @param [in]shmflg:Specifies a set of flags that indicate the specific shared.
* memory conditions and options to implement.
* shmflg=0:read &write; shmflg=SHM_RDONLY:read only;
* @return: failed:-1;success:points to the desired address
*/
STATIC INLINE void *ToolShmAt(int32_t shmid, const void *shmaddr, int32_t shmflg)
{
return shmat(shmid, shmaddr, shmflg);
}
* @brief: detaches the shared memory segment located at the address specified by
* shmaddr. from the address space of the calling process.
* @param [in]shmaddr: the data segment start address of a shared memory segment
* @return: failed:-1;succeed:0;
*/
STATIC INLINE int32_t ToolShmDt(const void *shmaddr)
{
return shmdt(shmaddr);
}
* @brief: shared memory control operations
* @param [shmid]shared memory ID
* @param [cmd]commond to do
* @param [in]buf:the structure pointed
* @return: failed:-1;succeed:0;
*/
STATIC INLINE int32_t ToolShmCtl(int32_t shmid, int32_t cmd, struct shmid_ds *buf)
{
return shmctl(shmid, cmd, buf);
}
* @brief : create shared memory
* @param [in/out]shmId: shared memory id
* @return succeed:SHM_SUCCEED,failed:SHM_ERROR
*/
ShmErr ShMemCreat(int32_t *shmId, toolMode perm)
{
if (shmId == NULL) {
return SHM_ERROR;
}
uint32_t shmFlag = IPC_CREAT | IPC_EXCL | (uint32_t)perm;
int32_t memId = ToolShmGet(MSG_MEMORY_KEY, SHM_SIZE, (int32_t)shmFlag);
if (memId == -1) {
SYSLOG_WARN("CreatShMem error, strerr=%s.try \"ipcs -m\" to check.\n", strerror(ToolGetErrorCode()));
return SHM_ERROR;
}
*shmId = memId;
return SHM_SUCCEED;
}
* @brief : open shared memory
* @param [out]shmId:identifier ID
* @return: SHM_SUCCEED/SHM_ERROR
*/
ShmErr ShMemOpen(int32_t *shmId)
{
if (shmId == NULL) {
return SHM_ERROR;
}
int32_t memId = ToolShmGet(MSG_MEMORY_KEY, 0, 0);
if (memId == (int)SHM_ERROR) {
return SHM_ERROR;
}
*shmId = memId;
return SHM_SUCCEED;
}
* @brief : write string to shared memory
* @param [in]shmId:share ID to identify shared memory
* @param [in]value:string to be write
* @param [in]len: max length of string
* @return: SHM_SUCCEED/SHM_ERROR
*/
ShmErr ShMemWrite(int32_t shmId, const char *value, uint32_t len, uint32_t offset)
{
if ((shmId == -1) || (value == NULL) || (len == 0)) {
SYSLOG_WARN("[input]shmId or value is error, shmId = %d\n ", shmId);
return SHM_ERROR;
}
char *shmvalue = (char *)ToolShmAt(shmId, NULL, 0);
if ((intptr_t)shmvalue == -1) {
SYSLOG_WARN("WriteToShMem shmat failed ,strerr=%s.\n", strerror(ToolGetErrorCode()));
return SHM_ERROR;
}
if (shmvalue == NULL) {
return SHM_ERROR;
}
int32_t ret = snprintf_truncated_s(shmvalue + offset, len, "%s", value);
if (ret < 0) {
return SHM_ERROR;
}
if (ToolShmDt(shmvalue) != (int)SHM_SUCCEED) {
SYSLOG_WARN("shmdt failed, strerr=%s.\n", strerror(ToolGetErrorCode()));
return SHM_ERROR;
}
return SHM_SUCCEED;
}
* @brief : read string from shared memory
* @param [in]shmId:share ID to identify shared memory
* @param [in]value:buffer to store string
* @param [in]len: max length of string
* @return: SHM_SUCCEED/SHM_ERROR
*/
ShmErr ShMemRead(int32_t shmId, char *value, size_t len, size_t offset)
{
if ((value == NULL) || (len == 0)) {
return SHM_ERROR;
}
char *shmvalue = (char *)ToolShmAt(shmId, NULL, SHM_RDONLY);
if ((intptr_t)shmvalue == -1) {
return SHM_ERROR;
}
if (shmvalue == NULL) {
return SHM_ERROR;
}
if ((strlen(shmvalue) == 0) || (strlen(shmvalue) > len)) {
return SHM_ERROR;
}
int32_t ret = snprintf_truncated_s(value, len, "%s", shmvalue + offset);
if (ret < 0) {
return SHM_ERROR;
}
if (ToolShmDt(shmvalue) != 0) {
return SHM_ERROR;
}
return SHM_SUCCEED;
}
* @brief : remove the shared memory
* @return: SHM_SUCCEED/SHM_ERROR
*/
void ShMemRemove(void)
{
int32_t shmId;
if (ShMemOpen(&shmId) == SHM_ERROR) {
return;
}
if (ToolShmCtl(shmId, IPC_RMID, NULL) != 0) {
SYSLOG_WARN("ToolShmCtl failed, strerr=%s.\n", strerror(ToolGetErrorCode()));
return;
}
return;
}