使用易失性变量的 C 函数示例

发布于 2024-07-11 20:05:51 字数 711 浏览 5 评论 0原文

对于一篇论文,我正在寻找一个使用易失性变量的现实 C 函数。 这本身并不难找到,但我正在寻找一个函数,其中 volatile 变量的值必须在函数执行过程中针对函数的特定分支发生变化达到。 像这样的事情:

typedef struct {
    unsigned       :6;
    unsigned FLAG1 :1;
    unsigned FLAG2 :1;
} __attribute__ ((packed)) REGISTER;

volatile REGISTER * io_ = 0x1234;

int write_to_io()
{
    while (io_->FLAG1) {};
    //io_->FLAG1 is now 0

    io_->FLAG2 = 1;

    sleep(10);

    if (io->FLAG1)  
        return 1;  //io->FLAG1 has changed from 0 to 1
    else
        return 0;  //io->FLAG1 has not changed
 }

如果结构的不同位在函数执行期间发生变化就足够了,但我的主要标准是,为了达到某个分支,易失性变量的值在期间 函数的执行。

我将非常感谢任何现实生活中的例子。 我在网上找不到很多使用 volatile 的例子。

for a paper I'm looking for an real-life C function which uses volatile variables. That in itself is not hard to find, but I am looking for a function in which the value of the volatile variable must change during the course of the execution of the function, for a particular branch of the function to be reached. Something like this:

typedef struct {
    unsigned       :6;
    unsigned FLAG1 :1;
    unsigned FLAG2 :1;
} __attribute__ ((packed)) REGISTER;

volatile REGISTER * io_ = 0x1234;

int write_to_io()
{
    while (io_->FLAG1) {};
    //io_->FLAG1 is now 0

    io_->FLAG2 = 1;

    sleep(10);

    if (io->FLAG1)  
        return 1;  //io->FLAG1 has changed from 0 to 1
    else
        return 0;  //io->FLAG1 has not changed
 }

It would be sufficient if different bits of the structure changed during the execution of the function, but my main criterion is that for a certain branch to be reached, the value of a volatile variable changes during the execution of the function.

I'd be very grateful for any real-life examples. I haven't been able to find many examples using volatile on the web.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

书信已泛黄 2024-07-18 20:05:51

规范(且可移植)的示例是处理异步信号。 (您可以使用 Ctrl-C 将 SIGINT 传递给您的程序)。

#include <signal.h>
#include <stdio.h>

volatile sig_atomic_t quit;

void signal_handler(int sig)
{
    signal(sig, signal_handler);
    quit = 1;
}

int main(void)
{
    signal(SIGINT, signal_handler);
    puts("Hit return to poll quit flag");
    while (!quit) getchar();
    return 0;
}

The canonical (and portable) example is handling an asynchronous signal. (You can probably deliver SIGINT to your program with Ctrl-C).

#include <signal.h>
#include <stdio.h>

volatile sig_atomic_t quit;

void signal_handler(int sig)
{
    signal(sig, signal_handler);
    quit = 1;
}

int main(void)
{
    signal(SIGINT, signal_handler);
    puts("Hit return to poll quit flag");
    while (!quit) getchar();
    return 0;
}
隱形的亼 2024-07-18 20:05:51

选择你最喜欢的开源操作系统,并寻找旧的设备驱动程序,你会发现一些没有其他工作方式。

Pick your favorite open source operating system, and look for old device drivers, you'll find some who have no other way of working.

深府石板幽径 2024-07-18 20:05:51

我老师的一些例子,它在一个编译器(lcc)的情况下无需 volatile 就可以工作,但是当我使用该处理器的 gcc 端口运行它时,它就崩溃了。 我必须放入 易失性 。

static int volatile busTimeoutSeen;

int busTimeoutISR(int irq) {
  busTimeoutSeen = 1;
  return 1;  /* skip offending instruction */
}


int memsize(void) {
  unsigned char volatile *ptr;
  unsigned char b;
  ISR oldService;

  busTimeoutSeen = 0;
  oldService = getISR(16);
  setISR(16, busTimeoutISR);
  ptr = (unsigned char *) 0xC0000000;
  while (1) {
    b = *ptr;
    if (busTimeoutSeen) {
      break;
    }
    ptr += (1 << 12);
  }
  setISR(16, oldService);
  return (ptr - (unsigned char *) 0xC0000000) >> 12;
}

它从所有页面连续读取,直到我们越过最后一页,这会导致中断,这会将 busTimeoutSeen 设置为 1。当这发生在幕后时,我们告诉编译器总是将数据读写到内存中。

Some example of my teacher, which worked without volatile with one compiler (lcc), but breaked when i run it with my gcc port for that processor. I had to put volatile in.

static int volatile busTimeoutSeen;

int busTimeoutISR(int irq) {
  busTimeoutSeen = 1;
  return 1;  /* skip offending instruction */
}


int memsize(void) {
  unsigned char volatile *ptr;
  unsigned char b;
  ISR oldService;

  busTimeoutSeen = 0;
  oldService = getISR(16);
  setISR(16, busTimeoutISR);
  ptr = (unsigned char *) 0xC0000000;
  while (1) {
    b = *ptr;
    if (busTimeoutSeen) {
      break;
    }
    ptr += (1 << 12);
  }
  setISR(16, oldService);
  return (ptr - (unsigned char *) 0xC0000000) >> 12;
}

It reads continuously from all pages, until we get past the last page, which causes an interrupt, which will set busTimeoutSeen to 1. As that happens behind the scenes, we tell the compiler to read and write the data always to memory.

孤单情人 2024-07-18 20:05:51

内存映射 IO 是一个示例,其中内存中的值实际上可能表示从 COM 端口等设备读取。 当我学习 C 时,这是使用 volatile 关键字的示例之一。

Memory mapped IO is an example where a value in memory may actually represent reading from a device such as a COM port. When I learned C, this was one of the examples given for the use of the volatile keyword.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文