精华内容
下载资源
问答
  • Linux2.4不支持内核抢占,即是说进程通过系统调用陷入到内核态的时候,不可以被其他的进程抢占。如果有更高优先级的进程,只有在系统调用返回用户空间的时候,才可被调度程序调度,由高优先级的进程占用cpu。这里的...

    Linux2.4不支持内核抢占,即是说进程通过系统调用陷入到内核态的时候,不可以被其他的进程抢占。如果有更高优先级的进程,只有在系统调用返回用户空间的时候,才可被调度程序调度,由高优先级的进程占用cpu。这里的“不可以被其他进程抢占”当然不包括中断上下文,无论内核态还是用户态,中断上下文都可以抢占进程上下文,中断上下文是拥有最高的权限,它甚至可以抢占其他的中断上下文。

    Linux2.6有一个CONFIG_PREEMPT的选项,打开该选项后,linux kernel就支持了内核代码的抢占。对于抢占式内核而言,即便是从中断上下文返回内核空间的进程上下文,只要内核代码不在临界区内,就可以发生调度,让最高优先级的任务调度执行。例如高优先级的进程可以抢占内核态的系统调用,而不必等系统调用执行完返回用户空间才抢占。

    展开全文
  • 作业 操作系统的cpu调度算法 完成SJF抢占优先算法 完成SJF非抢占算法 完成时间片轮转算法 完成express的文件上传
  • 一、脚本语言的可抢占能力 根据脚本引擎核心的抢占能力,脚本引擎大概可分三类: 1. 第一类脚本,它的语句是细粒度的,而且如果它没有完成所有命令,就不能被宿主抢占(脚本不能被打断)。 例如Python,它提供的...

     

    一、脚本语言的可抢占能力

    根据脚本引擎核心的抢占能力,脚本引擎大概可分三类:

    1. 第一类脚本,它的语句是细粒度的,而且如果它没有完成所有命令,就不能被宿主抢占(脚本不能被打断)。

    例如Python,它提供的PyRun_SimpleString是不可抢占(除非它自己退出,或在脚本运行于一个后台线程内)

        2. 第二类脚本,它实际上是宏命令集合(相当于描述或配置文件)。它的执行过程可以被宿主打断。

        例如XML,它的执行(实际上是解析)速度很快。脚本既可以一次性地向宿主传递数据就马上退出,也可以以单步的形式在脚本解析和宿主执行之间轮流切换。

        3. 第三类脚本,它们的虚拟机核心部分是可抢占的,即脚本自身可以暂停或挂起自己,通过退出虚拟机把控制权交还宿主。等待宿主完成某些事情后重新恢复脚本的执行。

        例如Lua,允许使用一种叫“协程”的机制,并且提供一个API叫lua_resume,使Lua和宿主的执行流能有尽可能多的机会交错切换(详细可以参考这个链接(日文):http://marupeke296.com/LUA_No3_Coroutine.html)。由于可抢占的优势,Lua可以轻松处理事件驱动的系统。只要它有机会挂起自己,就能避免“程序无响应”的情况(前提是脚本执行的时间粒度足够小)。

     

    二、如何让非抢占脚本引擎与消息循环共存

    如上所述,脚本的可抢占能力与实时事件的处理能力是相关联的。如果脚本不需要花太多的时间(不处理鼠标事件),那么能否被抢占是无需考虑的。但万一脚本需要花很多时间(需要处理鼠标事件),而且脚本不可抢占,那么程序就可能困死在脚本中,没有时间处理窗口事件。

    问题是:如果选择的脚本语言是单线程(同一时间只能执行一段脚本)且不可抢占(阻塞的),如何让它和实时系统(窗口系统)共存。

    我认为解决方法有以下几种:

    1. 多线程

    由于脚本的执行是同步的,与异步的窗口事件处理不兼容,可以显式地创建一个后台线程,让脚本的执行独立于窗口系统,通过线程间的共享内存进行通信。需要考虑多线程的数据竞争问题。

    2. 在脚本内处理窗口系统的消息循环

    由于Windows的窗口处理实际上是多线程的,可以让主线程的消息循环在脚本内执行,使窗口事件的处理不被阻塞。虽然这种方法没有显式创建线程,但原理实际上和方法1相同。

    3. 与可抢占的脚本语言混合使用

    使用多于一种脚本引擎来操纵程序。需要考虑不同脚本状态机之间的数据共享问题。

    4. 把一个脚本分拆成多个脚本

    让窗口事件处理(如鼠标事件)的逻辑单独放在一个脚本文件。不过如果脚本状态机不是全局的,还需要留意状态数据的共享问题。

    我觉得第2种办法是最优雅的,因为它不需要太复杂的机制。不过这么做的话,脚本既要处理逻辑,还要处理底层。

     

    三、简单地在Python脚本中嵌入Win32消息循环

    我尝试用第2种解决方法在Win32窗口程序内嵌入Python 2.2.2脚本(模仿一个日本游戏引擎KAVG的做法)。

    大概写法如下(注意,这里忽略脚本的错误信息输出和窗口输入处理,而且用PyRun_SimpleString不太好,仅供参考)

     

    脚本引擎部分:

     

     

    #include <Python.h>
    #include <windows.h>
    #include "script.h"
    #include "mainframe.h"
    
    static PyObject *trace(PyObject *self, PyObject *args)
    {
        char* input;
        if (!PyArg_ParseTuple(args, "s", &input))
    	{
    		return NULL;
    	}
    	OutputDebugString(input);
    	OutputDebugString("\n");
    	return PyInt_FromLong(0);
    }
    
    static PyObject *foo(PyObject *self, PyObject *args)
    {
    	return PyInt_FromLong(42L);
    }
    
    static PyObject *peekMsg(PyObject *self, PyObject *args)
    {
    	return PyInt_FromLong(MainFrameMainLoop());
    }
    
    void PyInit_SAVG(void)
    {
    	PyObject *m;
    	static PyMethodDef SAVG_methods[] = {
    		//{"foo", (PyCFunction)foo, METH_NOARGS, "Return the meaning of everything."},
    		{"trace", (PyCFunction)trace, METH_VARARGS, "Output debug info for debugging."},
    		{"peekMsg", (PyCFunction)peekMsg, METH_NOARGS, "Window message loop"},
    		{NULL, NULL}
    	};
    	PyImport_AddModule("SAVG");
    	m = Py_InitModule("SAVG", SAVG_methods);
    	PyModule_AddStringConstant(m, "SAVG_VERSION", SAVG_VERSION);
    }
    
    static int script_init(void)
    {
    	int ret;
    	ret = PyRun_SimpleString(
    		"import SAVG\n"
    		"SAVG.trace(\"Script environment is initializing...\")\n"
    		"SAVG.trace(\"SAVG_VERSION is %s\" % SAVG.SAVG_VERSION)\n"
    	);
    	if(ret == -1)
    	{
    		OutputDebugString("error on script_init\n");
    		return 0;
    	}
    	return 1;
    }
    
    static void script_main(void)
    {
    	int ret;
    	ret = PyRun_SimpleString(
    		"while 1:\n"
    		"	if SAVG.peekMsg():\n"
    		"		break\n"
    	);
    	if(ret == -1)
    	{
    		OutputDebugString("error on script_main\n");
    	}
    }
    
    //NOTE:This function is in WinMain (Main Thread)
    int runScript(void)
    {
    	Py_SetProgramName("SimpleScriptSystem");
    	Py_Initialize();
    	PyInit_SAVG();
    	if(script_init())
    	{
    		script_main();
    	}
    	Py_Finalize();
    	return 0;
    }
    

     

     

    主窗口(部分代码):

     

     

    int APIENTRY _tWinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPTSTR lpCmdLine, int nCmdShow)
    {
    	UNREFERENCED_PARAMETER(hPrevInstance);
    	UNREFERENCED_PARAMETER(lpCmdLine);
    	MyRegisterClass(hInstance);
    	if(!InitInstance(hInstance, nCmdShow))
    	{
    		return FALSE;
    	}
    	//TODO: Using script engine to dispatch message,
    	//or the main window will have no response!!!
    	//As follow:
    	//	while(1)
    	//	{
    	//		if(MainFrameMainLoop())
    	//			break;
    	//	}
    	runScript();
    	//FIXME:
    	//the return value of program should be : 
    	//(int) msg.wParam;
    	return 0; 
    }
    
    int MainFrameMainLoop(void) 
    {
    	MSG msg;
    	if(!GetMessage(&msg, 0, 0, 0))
    	{
    		return 1;
    	}
    	if(!TranslateAccelerator(msg.hwnd, NULL, &msg)) 
    	{
    		TranslateMessage(&msg);
    		DispatchMessage(&msg);
    	}
    	return 0;
    }
    

     

     

    原本执行GetMessage的循环被Python脚本接管了,所以即使script_main没有执行完,窗口系统也不会失去响应。

    此时Python脚本不能直接处理输入事件,只能在peekMsg之后轮询输入缓冲(上面的代码没有实现此功能)。

     

    四、总结

    用类似Python的不可抢占脚本语言处理实时事件是可以的,关键是让脚本内的微观操作尽快完成,但不需要让整个脚本尽快完成。在山穷水尽的时候,还可以依靠操作系统的多线程能力。

    对于win32消息循环,Python脚本可以通过C扩展来避免使用协程。

     

    五、参考资料

    1. Lua組み込み編:その3 コルーチンで状態遷移をLuaで制御

    http://marupeke296.com/LUA_No3_Coroutine.html

    2. Lua下实现抢占式多线程

    http://blog.codingnow.com/2011/08/lua_52_multithreaded.html

    3. 游戏引擎脚本系统(二)

    http://www.blogjava.net/tianlinux/archive/2007/06/01/121434.html

     

     
    展开全文
  • keepalived抢占模式和非抢占模式

    千次阅读 2020-01-04 15:42:48
    1,抢占式 抢占模式为当keepalived的某台机器挂了之后VIP漂移到了备节点,当主节点...非抢占模式则是当主节挂了再次起来后不再抢回VIP。 两个节点的state都必须配置为BACKUP,两个节点都必须加上配置 nopreempt。 ...
    1,抢占式

    抢占模式为当keepalived的某台机器挂了之后VIP漂移到了备节点,当主节点恢复后主动将VIP再次抢回,keepalived默认工作在抢占模式下。
    主节点MASTER,备节点BACKUP

    2,非抢占式

    非抢占模式则是当主节挂了再次起来后不再抢回VIP。
    两个节点的state都必须配置为BACKUP,两个节点都必须加上配置 nopreempt。

    展开全文
  • 抢占式与非抢占式调度When the CPU is in the idle state, the CPU scheduler chooses a process from the ready queue and allocates the process to CPU. There are two types of scheduling, 当CPU处于空闲状态...

    抢占式与非抢占式调度

    When the CPU is in the idle state, the CPU scheduler chooses a process from the ready queue and allocates the process to CPU. There are two types of scheduling,

    当CPU处于空闲状态时,CPU调度程序从就绪队列中选择一个进程,并将该进程分配给CPU。 调度有两种类型,

    1. Preemptive Scheduling

      抢占式调度

    2. Non-Preemptive Scheduling

      非抢占式调度

    1)抢占式调度 (1) Preemptive Scheduling)

    Once a process started its execution, scheduling occurs at the time of a process switches from running state to ready state and from waiting state to ready state is called Preemptive Scheduling.

    一旦进程开始执行,调度就在进程从运行状态切换到就绪状态以及从等待状态切换到就绪状态时发生,称为抢先调度。

    In this scheduling resources (CPU cycles) are allocated to the process for a short period of time and if some process of higher priority is encountered then the current process can be paused to handle that process.

    在这种调度中,资源(CPU周期)会在短时间内分配给该进程,如果遇到某些优先级更高的进程,则可以暂停当前进程以处理该进程。

    • Then resources from the currently running process taken away, and the currently running process is placed back in the ready queue again if it still has remaining CPU burst time. That is we can preempt the control of CPU from one process to another if required. The process remains in a ready queue till it gets the next time slot to get executed.

      然后,如果仍然有剩余的CPU突发时间,则会从当前正在运行的进程中删除资源,并将当前正在运行的进程再次放回到就绪队列中。 也就是说,如果需要,我们可以抢先将CPU的控制从一个进程转移到另一个进程。 该过程将一直处于就绪队列中,直到获得下一个要执行的时隙为止。

    • By implementing this type of scheduling user can work on multiple processes that are it supports multitasking.

      通过实现这种类型的调度,用户可以在支持多任务的多个进程上工作。

    • Examples of Preemptive Scheduling are Round Robin (RR), Shortest Remaining Time First (SRTF), Priority (preemptive version), etc.

      抢占式调度的示例包括循环调度(RR),最短剩余时间优先(SRTF),优先级(抢占版本)等。

    2)非抢占式调度 (2) Non-Preemptive Scheduling)

    Once a process started its execution, scheduling occurs when a process terminates, or a process switches from running to waiting state.

    一旦进程开始执行,调度将在进程终止或进程从运行状态切换到等待状态时进行。

    • When the resources (CPU) are allocated to a process, the process holds the CPU till it gets terminated or it reaches a waiting state.

      当将资源(CPU)分配给进程时,该进程将保持CPU直到其终止或达到等待状态。

    • In non-preemptive scheduling, the scheduler does not interrupt a currently running process in the middle of the execution. But it waits for the process to complete its execution with the CPU, after that it can allocate the CPU to another process.

      在非抢占式调度中,调度程序在执行过程中不会中断当前正在运行的进程。 但是它等待进程完成其与CPU的执行,然后可以将CPU分配给另一个进程。

    • FCFS scheduling is an example of non-preemptive scheduling.

      FCFS调度是非抢占式调度的一个示例。

    抢占式和非抢占式调度之间的区别 (Differences between Preemptive and Non-Preemptive Scheduling in OS)

    • In the middle of the execution of a process the execution is interrupted whereas; in non-preemptive scheduling, execution is not interrupted in the middle of execution.

      在执行过程的中间,执行被中断,而; 在非抢占式调度中,在执行过程中不会中断执行。

    • Preemptive Scheduling suffers from the overhead of switching between processes from the ready state to running state, vice-verse, and maintaining the ready queue. On the other hand, non-preemptive scheduling does not suffer from the overhead of switching the process from running state to ready state.

      抢先式调度会遭受从就绪状态到运行状态(反之亦然)之间进行切换以及维护就绪队列的开销。 另一方面,非抢占式调度不会遭受将进程从运行状态切换到就绪状态的开销。

    • When a high priority process arrives frequently in the ready queue then the process with low priority has to wait for a long time, and it may have to starve, in preemptive scheduling. Whereas in the non-preemptive scheduling, if CPU is allocated to the process with larger burst time then the processes with smallest burst time may have to starve.

      当高优先级的进程频繁到达就绪队列时,低优先级的进程必须等待很长时间,并且可能会在抢占式调度中饿死。 而在非抢占式调度中,如果将CPU分配给具有较大突发时间的进程,则突发时间最小的进程可能不得不挨饿。

    • The critical processes are allowed to access CPU whenever they arrive into the read queue. In this way preemptive scheduling is flexible. While non-preemptive scheduling is rigid because if a critical process enters the ready queue the process running CPU not disturbed.

      只要关键进程进入读取队列,就可以访问它们。 这样,抢占式调度是灵活的。 非抢占式调度很严格,因为如果关键进程进入就绪队列,则运行CPU的进程不会受到干扰。

    • The Preemptive Scheduling has to maintain the integrity of shared data so it is cost associative but it is not the case with non-preemptive Scheduling.

      抢先式调度必须维护共享数据的完整性,因此这与成本相关,但非抢先式调度则不是这种情况。

    • The main difference between these two schedules is that in non-preemptive scheduling, the CPU is allocated to the process till it completes its execution or switches from running state to waiting state. Whereas in preemptive scheduling the CPU is allocated to a process for a limited amount of time.

      这两个调度之间的主要区别在于,在非抢占式调度中,CPU被分配给进程,直到它完成执行或从运行状态切换到等待状态。 而在抢占式调度中,CPU将在有限的时间内分配给某个进程。

    References:

    参考文献:

    翻译自: https://www.includehelp.com/operating-systems/preemptive-vs-non-preemptive-scheduling.aspx

    抢占式与非抢占式调度

    展开全文
  • 抢占式和非抢占

    千次阅读 2019-08-29 14:42:45
    抢占式内核与半抢占式内核的不同 Linux2.4只实现了“有条件抢占式”的调度。它的缺点在于:当进程在内核态时,调度的时机有局限。就是只能在xxx的前夕。例如:当外部来一中断,中断程序过程完后,需要一个用户进程...
  • keepalived的高可用,分为抢占模式和非抢占模式,抢占模式是当master从故障中恢复后,会将VIP从BACKUP中抢过来,非抢占模式是master恢复后不抢占backup升级为master后的vip。 有如下机器: global_defs { ... } ...
  • 非抢占式实时操作系统Here you will learn about difference between ... 在这里,您将了解os中抢占式和非抢占式调度之间的区别。 Preemptive Scheduling 抢占式调度 Preemptive Scheduling means once a pr...
  • 抢占式和非抢占式内核

    千次阅读 2017-12-27 10:07:30
    非抢占式内核非抢占式内核:高优先级的进程不能中止正在内核中运行的低优先级的进程而抢占CPU运行。进程一旦处于核心态(例如用户进程执行系统调用),则除非进程自愿放弃CPU,否则该进程将一直运行下去,直至完成或...
  • keepalived的高可用,分为抢占模式和非抢占模式,抢占模式是当master从故障中恢复后,会将VIP从BACKUP中抢过来,非抢占模式是master恢复后不抢占backup升级为master后的vip。 有如下机器: 类别 主备 IP ip1...
  • 线程的抢占式和非抢占式调度

    千次阅读 2019-03-14 16:48:33
    在一个进程里,线程的调度有抢占式或者非抢占的模式。 在抢占模式下,操作系统负责分配CPU时间给各个进程,一旦当前的进程使用完分配给自己的CPU时间,操作系统将决定下一个占用CPU时间的是哪一个线程。因此...
  • 非抢占抢占式进程调度都属于最高优先级进程调度。 采用非抢占式最高优先级调度算法,当**就绪队列**中某进程的最高优先级高于正在**处理器**中运行的进程的最高优先级时,并不会让正在运行的进程退出处理器,...
  • 抢占式和非抢占式的进程调度

    千次阅读 2017-02-19 20:17:09
    非抢占式(Nonpreemptive) 让进程运行直到结束或阻塞的调度方式 容易实现 适合专用系统,不适合通用系统 抢占式(Preemptive)  允许将逻辑上可继续运行的在运行过程暂停的调度方式 可防止单一进程长时间独占CPU...
  • 抢占式内核和非抢占式内核的区别

    千次阅读 2020-01-02 17:55:59
    非抢占式内核:高优先级的进程不能中止正在内核中运行的低优先级的进程而抢占CPU运行。进程一旦处于核心态(例如用户进程执行系统调用),则除非进程自愿放弃CPU,否则该进程将一直运行下去,直至完成或退出内核 ...
  • 抢占模式下,优先级决定VIP的归属 经实验测试,抢占还是看priority的参数 实验环境1: 服务器1 state MASTER priority 100 服务器2 state BACKUP priority 100 测试结果: 第一次启动,MASTER会先转换MASTER状态...
  • Keepalived抢占模式和非抢占模式: keepalived的HA分为抢占模式和非抢占模式,抢占模式即MASTER从故障中恢复后,会将VIP从BACKUP节点中抢占过来。 非抢占模式即MASTER恢复后不抢占BACKUP升级为MASTER后的VIP。 ...
  • 非抢占模式:backup路由器工作于该模式下时,只要master路由器不出现故障,则维持原状。 VRRP的优势: 冗余:可以使用多个路由器设备作为LAN客户端的默认网关,大大降低了默认网关成为单点故障的可能性; 负载...
  • 操作系统【处理机调度算法作业(调度算法下的调度时间图:FCFS、抢占式\非抢占式SPF、抢占式\非抢占式HPF、HRRNRR)】 简述死锁的定义、死锁产生的原因、以及处理死锁的方法。
  • 描述操作系统抢占式和非抢占式算法的可视化简单操作界面,主要利用java-swing构建窗口,利用数组完成算法,采用Graphics2D画图完成。
  • (1) linux上的自旋锁有三种实现:  1. 在单cpu,不可抢占内核中,自旋锁为空操作。  2. 在单cpu,可抢占内核中,自旋锁实现为“禁止内核抢占”,并...  3....(2) 关于抢占式内核与非抢占式内核: ... 在非抢占式内
  • 突然回去看概念,中间很多协议之前的抢占与非抢占完全记糊涂了。 所以单独写一份用于记忆。 协议  角色 模式 备注 OSPF DR-BDR 非抢占 当一个OSPF路由器启动并开始搜索邻居时,它先搜寻活动的DR...
  • 抢占和抢占式进程调度的区别是什么?

    万次阅读 多人点赞 2018-04-14 00:18:51
    1) 非抢占式优先权算法在这种方式下,系统一旦把处理机分配给就绪队列中优先权最高的进程后,该进程便一直执行下去,直至完成;或因发生某事件使该进程放弃处理机时,系统方可再将处理机重新分配给另一优先权最高的...
  • 一、自旋锁的实现 linux上的自旋锁有三种实现: 1. 在单cpu,不可抢占内核中,自旋锁为空操作。...关于抢占式内核与非抢占式内核: a、非抢占式内核 如果一个进程在内核态运行,其只有在以下两种情况会被切换: 1.
  • 线程的调度有抢占式或者非抢占

    千次阅读 2012-08-28 18:50:48
    在一个进程里,线程的调度有抢占式或者非抢占的模式。 在抢占模式下,操作系统负责分配CPU时间给各个进程,一旦当前的进程使用完分配给自己的CPU时间,操作系统将决定下一个占用CPU时间的是哪一个线程。...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 862
精华内容 344
关键字:

抢占和非抢占