2017-01-18 4 views
3

Ich möchte eine neue Arbeitswarteschlange create_workqueue()Erstellt 'create_workqueue()' einen neuen Arbeitsthread?

Der Autor des Buches über die Kernel-Entwicklung Ich lese sagt: „Diese Funktion erzeugt alle Worker-Threads (einen für jeden Prozessor im System) und bereitet sie mit schaffen Arbeit erledigen. "

Mein Code am Ende dieser Frage erstellt einen Kernel und plant die Arbeit an zwei Warteschlangen. Eine ist eine Standardwarteschlange und die andere verwendet eine angepasste Arbeitswarteschlange. Sie sollten von verschiedenen Worker-Threads bearbeitet werden.

Allerdings sehe ich in den Ergebnissen (siehe unten) beide werden durch den gleichen Prozess (PID 42501) behandelt, der der Thread kworker2 in meiner virtuellen Maschine ist.

Run Ergebnis: running result

thread details

#include <linux/workqueue.h> 
#include "kn_common.h" 
#include <linux/sched.h> 

MODULE_LICENSE("Dual BSD/GPL"); 

static void my_work_func(struct work_struct *work){ 
    long ID; 
    printk(KERN_ALERT"=============\n"); 
    print_current_time(0); 
    ID = current->pid; 
    printk(KERN_ALERT"my workqueue function is called!.... pid = %ld\n", ID); 
    printk(KERN_ALERT"=============\n"); 
} 

static void my_work_custom_func(struct work_struct *work){ 
    long ID; 
    printk(KERN_ALERT"=============\n"); 
    print_current_time(0); 
    ID = current->pid; 
    printk(KERN_ALERT"my customize workqueue is called!... pid = %ld\n", ID); 
    printk(KERN_ALERT"=============\n"); 
} 

DECLARE_WORK(mywork, my_work_func); 

static int testworkqueue_init(void){ 
    struct workqueue_struct *myworkqueue = create_workqueue("myworkqueue"); 

    // init a work_struct dynamically use pointer 
    struct work_struct *mywork2; 
    mywork2 = kmalloc(sizeof(struct work_struct), GFP_KERNEL); 
    INIT_WORK(mywork2, my_work_custom_func); 

    flush_scheduled_work(); 

    // schedule work 
    schedule_work(&mywork); 

    // flush customized workqueue 
    flush_workqueue(myworkqueue); 
    queue_work(myworkqueue, mywork2); 

    return 0; 
} 

static void testworkqueue_exit(void){ 
    printk(KERN_ALERT"*************\n"); 
    print_current_time(0); 
    printk(KERN_ALERT"testworkqueu exit\n"); 
    printk(KERN_ALERT"*************\n"); 
} 

module_init(testworkqueue_init); 
module_exit(testworkqueue_exit); 

Und Makefile

obj-m += myworkqueue.o 
myworkqueue-objs := testworkqueue.o kn_common.o 


CURRENT_PATH := $(shell pwd) 

LINUX_KERNEL := $(shell uname -r) 
# you may change this to your own kernel src path 
LINUX_KERNEL_PATH := /lib/modules/$(LINUX_KERNEL)/build 

all: 
    make -C $(LINUX_KERNEL_PATH) M=$(CURRENT_PATH) modules 
    rm -rf modules.order Module.symvers .*.cmd *.o *.mod.c .tmp_versions *.unsigned 

clean: 
    rm -rf modules.order Module.symvers .*.cmd *.o *.mod.c *.ko .tmp_versions *.unsigned 

Antwort

0

Ursprünglich Multi-Thread (MT) Workqueue implementiert viele Ressourcen verschwendet, die Höhe der Gleichzeitigkeit vorgesehen war ungenügend.

Neues Design wurde eingeführt, um ein hohes Maß an Parallelität zu erreichen. Funktionen "create_ * workqueue()" sind veraltet und zum Entfernen geplant.

Bitte lesen Sie this für die neueste Implementierung der Workqueue.

Verwandte Themen