gpt4 book ai didi

c++ - 我们可以在 c++20 协程中使用 alloca() 或可变长度数组扩展吗?

转载 作者:行者123 更新时间:2023-12-04 11:32:35 25 4
gpt4 key购买 nike

GCC C++ 编译器(以及许多其他 C++ 编译器)提供非标准扩展,例如

  • alloca()用于基于堆栈的分配
  • 可变长度数组,因为它们是 C 标准的一部分

  • 从基本的角度来看,这些可以在 C++20 协程中使用吗?有可能吗?如果是,这是如何实现的?
    据我了解,C++20 协程通常在第一次调用时(即创建 promise 对象时)为协程创建堆栈帧,因此需要知道协程堆栈帧的大小。
    然而,这在 alloca 或其他运行时动态堆栈分配中并不能很好地发挥作用。
    那么是否有可能,如果是,它是如何实现的?或者有什么影响?

    最佳答案

    不幸的是,alloca与 GCC 中的 C++20 协程不兼容。最糟糕的是编译器没有警告它。
    此代码示例演示了不兼容性:

    #include <coroutine>
    #include <iostream>

    struct ReturnObject {
    struct promise_type {
    unsigned * value_ = nullptr;

    void return_void() {}
    ReturnObject get_return_object() {
    return {
    .h_ = std::coroutine_handle<promise_type>::from_promise(*this)
    };
    }
    std::suspend_never initial_suspend() { return {}; }
    std::suspend_never final_suspend() noexcept { return {}; }
    void unhandled_exception() {}
    };

    std::coroutine_handle<promise_type> h_;
    operator auto() const { return h_; }
    };

    template<typename PromiseType>
    struct GetPromise {
    PromiseType *p_;
    bool await_ready() { return false; }
    bool await_suspend(std::coroutine_handle<PromiseType> h) {
    p_ = &h.promise();
    return false;
    }
    PromiseType *await_resume() { return p_; }
    };

    ReturnObject counter()
    {
    auto pp = co_await GetPromise<ReturnObject::promise_type>{};

    //unsigned a[1]; auto & i = a[0]; //this version works fine
    auto & i = *new (alloca(sizeof(unsigned))) unsigned(0); //and this not
    for (;; ++i) {
    pp->value_ = &i;
    co_await std::suspend_always{};
    }
    }

    int main()
    {
    std::coroutine_handle<ReturnObject::promise_type> h = counter();
    auto &promise = h.promise();
    for (int i = 0; i < 5; ++i) {
    std::cout << *promise.value_ << std::endl;
    h();
    }
    h.destroy();
    }
    https://gcc.godbolt.org/z/8zG446Esx
    它应该打印 0 1 2 3 4 ,但不完全是由于 alloca 的用法

    关于c++ - 我们可以在 c++20 协程中使用 alloca() 或可变长度数组扩展吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/67576168/

    25 4 0
    Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
    广告合作:1813099741@qq.com 6ren.com