共享内存是linux进程间通信的一种方式,实现多进程共享变量。应用共享内存时,主要涉及shmget、shmat、shmdt、shmctl四个函数。

此外,可通过ipcs -m来查看linux共享内存使用情况。

下面展示一个本人编写的一应用实例。

/**
 * \File	test_shm.c
 *
 * COPYRIGHT (C) 2016 http://velep.com/
 *
 * \brief	linux共享内存测试程序
 * 			使用共享内存,实现多进程共享变量
 * 
 * \version: Ver1.0
 * \Date   : 2016.01.10
 * \Decrip : 原始版本
 */
 
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <errno.h>
#include <unistd.h>
#include <sys/shm.h>
#include <sys/stat.h>
#include <sys/time.h>
#include <sys/types.h>
#include <sys/wait.h>


// 基本类型定义
#define true        1
#define false       0

typedef unsigned char        bool;
typedef unsigned char        byte;
typedef unsigned char        __u8;
typedef unsigned int         __u32;

// 共享内存数据结构
typedef struct struct_context
{
    __u8            data;
} context_t;

// 全局变量定义
static bool  run = true;
context_t *g_pcontext = NULL;

// ----------------------------------------------------------------------------

void delay_ms(const __u32 ms)
{
    struct timespec tv;

    tv.tv_sec = ms / 1000;
    tv.tv_nsec = (long)(ms % 1000) * 1000000;

    nanosleep(&tv, NULL);
}

// 信号处理
void sig_handler(int signo) 
{ 
    switch(signo)
    {
    case SIGINT:
        run = false;
        printf(".Exit\n");
        break;

    default: break;
    }
}

// 安装信号
void install_sig(void) 
{ 
    signal(SIGINT, sig_handler);
}

int main(int argc, char **argv)
{
	pid_t pid = -1;
	int shmid;// id for shared memory
	int status = 0;
	
	// 创建一个新的共享内存对象
	shmid = shmget(IPC_PRIVATE, sizeof(context_t), S_IRUSR | S_IWUSR);
	// 映射共享内存
    g_pcontext = (context_t *)shmat(shmid, NULL, 0);
    if (g_pcontext == NULL)
    {
        printf("\n\t创建共享内存失败\n\n");
        return  -1;
    }
    memset(g_pcontext, 0x00, sizeof(*g_pcontext));
	
	printf("\n创建共享内存: shmid [%d], size [%d]\n", 
			shmid, sizeof(context_t));
	
	// 显示共享内存的情况 
	system("ipcs -m");		

    run = true;
	
	pid = fork();
    if (pid == -1) 
    { 
        printf("\n\t创建进程失败\n\n");
        run = false;
    }
    else if (pid == 0) // 子进程
    {
        while (run)
        {
			if (g_pcontext->data >= 3)
			{
				delay_ms(1000);
				g_pcontext->data++;
				printf("子进程,data [%u]\n", g_pcontext->data);		
				if (g_pcontext->data >= 6)
				{
					break;
				}
				continue;
			}
			delay_ms(10);
		}		
	}
	else // 父进程
    {
        install_sig();
		
        while (run)
        {			
			g_pcontext->data++;
			printf("父进程,data [%u]\n", g_pcontext->data);
			if (g_pcontext->data >= 3)
			{
				break;
			}
			
			delay_ms(1000);
		}			
		
		// 等待子进程退出
        while(((pid = wait(&status)) == -1) && (errno == EINTR))
        {
            delay_ms(10);
        }
	}
	
    shmdt(g_pcontext);// 解除共享内存映射
    shmctl(shmid, IPC_RMID, NULL);// 释放共享内存
	
	// 显示共享内存的情况 
	system("ipcs -m");	
	
	return	0;
}
» 文章出处: reille博客—http://velep.com , 如果没有特别声明,文章均为reille博客原创作品
» 郑重声明: 原创作品未经允许不得转载,如需转载请联系reille#qq.com(#换成@)
分享到:

 Leave a Reply

(必须)

(我会替您保密的)(必须)

*

This site uses Akismet to reduce spam. Learn how your comment data is processed.

   
© 2012 velep.com | reille blog | 管理| 粤ICP备15065318号-2| 谷歌地图| 百度地图| Suffusion theme|Sayontan Sinha

无觅相关文章插件,快速提升流量