вызов функции внутри функции без параметров - PullRequest
0 голосов
/ 11 мая 2018

Вызов функции без вызова ее параметров внутри другой функции немного сбивает с толку:

ppp = pppos_create(&ppp_netif, output_cb, status_cb, 0);

Где output_cb и status_cb - функции, параметры которых не установлены, и их определения должнызаписываться в верхних строках, чем те, которые они называют.

Определения функций:

static void status_cb(ppp_pcb *pcb, int err_code, void *ctx) {

    struct netif *pppif = ppp_netif(pcb);

    switch(err_code) {
        case PPPERR_NONE: {
            printf("status_cb: Connected\n");
            printf("   our_ipaddr  = %s\r\n", ipaddr_ntoa(&pppif->ip_addr));
            printf("   his_ipaddr  = %s\r\n", ipaddr_ntoa(&pppif->gw));
            printf("   netmask     = %s\r\n", ipaddr_ntoa(&pppif->
            break;
        }
        case PPPERR_PARAM: {
            printf("status_cb: Invalid parameter\r\n");
            break;
        }
    }
}

static u32_t output_cb(ppp_pcb *pcb, u8_t *data, u32_t len, void *ctx)
{
    return HAL_UART_Transmit_IT(&huart1, data, sizeof(data));
}

int main(void)
{
    ppp = pppos_create(&ppp_netif, output_cb, status_cb, 0);
}

Что печатает status_cb без указания err_code в качестве параметра?Когда или как будут оцениваться status_cb и output_cb?

Где pppos_create определяется следующим образом:

ppp_pcb *pppos_create(struct netif *pppif, pppos_output_cb_fn output_cb,
       ppp_link_status_cb_fn link_status_cb, void *ctx_cb)
{
    pppos_pcb *pppos;
    ppp_pcb *ppp;

    pppos = (pppos_pcb *)LWIP_MEMPOOL_ALLOC(PPPOS_PCB);
    if (pppos == NULL) {
        return NULL;
    }

    ppp = ppp_new(pppif, &pppos_callbacks, pppos, link_status_cb, ctx_cb);
    if (ppp == NULL) {
        LWIP_MEMPOOL_FREE(PPPOS_PCB, pppos);
        return NULL;
    }

    memset(pppos, 0, sizeof(pppos_pcb));
    pppos->ppp = ppp;
    pppos->output_cb = output_cb;
    return ppp;
}

С уважением

1 Ответ

0 голосов
/ 11 мая 2018

Вызов функции без вызова ее параметров внутри другой функции немного сбивает с толку следующим образом:

ppp = pppos_create(&ppp_netif, output_cb, status_cb, 0);

Где output_cb и status_cb являются функциями [...]

output_cb и status_cb - это не функция , вызовы , а скорее указатели . Имя функции без заключенного в скобки списка параметров является указателем на функцию, а не ее вызовом. Указатель на функцию позволяет вызывать функцию, не зная, какая функция будет вызываться во время компиляции / компоновки. В этом случае используются как обратные вызовы , так что предопределенная библиотечная функция может вызывать функцию пользовательского приложения.

Простой пример указателя на функцию:

Дано:

int someFunction( int arg ) 
{
    return( arg ) ;
}

Вы можете объявить указатель на функцию fp переменная таким образом:

int (*fp)(int) = someFunction ;

Затем вы можете вызвать someFunction функцию через fp, таким образом:

int x = fp( 2 ) ;

Что печатает status_cb без указания в качестве параметра err_code? Когда или как будут оцениваться status_cb и output_cb?

Аргументы функций предоставляются во время их вызова, а не во время их передачи pppos_create(). В pppos_create() они присваиваются output_cb и , link_status_cb parameters respectively. They have type pppos_output_cb_fn and ppp_link_status_cb_fn which will be typedef для типов указателей функций, например:

typedef void (*ppp_link_status_cb_fn)(ppp_pcb *, int, void*);

В этом случае pppos_create() не вызывает эти функции; скорее это назначение их членам структур данных pppos и ppp, которые, вероятно, будут вызываться позже всякий раз, когда происходят связанные события PPP (я предполагаю, что это функция, связанная с протоколом точка-точка). В этом случае они являются способом обеспечения пользовательской обработки предварительно определенной функции.

...