百科狗-知识改变命运!
--

sem_acquire() - semaphore函数

是丫丫呀12个月前 (11-21)阅读数 10#技术干货
文章标签返回值

sem_acquire()

(PHP 4, PHP 5, PHP 7)

Acquire a semaphore

说明

sem_acquire(resource $sem_identifier[,bool $nowait= FALSE]): bool

sem_acquire() by default blocks(if necessary)until the semaphore can be acquired. A process attempting to acquire a semaphore which it has already acquired will block forever if acquiring the semaphore would cause its maximum number of semaphore to be exceeded.

After processing a request, any semaphores acquired by the process but not explicitly released will be released automatically and a warning will be generated.

参数

$sem_identifier

$sem_identifieris a semaphore resource, obtained from sem_get().

$nowait

sem_acquire() - semaphore函数

Specifies if the process shouldn't wait for the semaphore to be acquired. If set totrue, the call will returnfalseimmediately if a semaphore cannot be immediately acquired.

返回值

成功时返回TRUE,或者在失败时返回FALSE

更新日志

版本说明
5.6.1 The$nowaitparameter was added.

参见

  • sem_get()Get a semaphore id
  • sem_release()Release a semaphore
sem_acquire() is blocking, meaning that subsequent calls with the same semaphore will block indefinitely until the semaphore is released. This ensures serialization, but it is not very practical if all you want to do is check if you should proceed or not. Unfortunately, PHP does not yet support any method of querying the state of a semaphore in a non-blocking manner.
It may seem possible to put together such a mechanism by hand, using shared memory (shm_ functions). However, be warned that it is not trivial and ultimately non-productive. You cannot, for example, simply pick a shared mem var, store the semaphore key and query it. Such an operation would be non-transactional and non-atomic ie. it is possible for two or more parallel processes to manage to read "not locked" from the shared mem var before one of them manages to mark it "locked". You would have to use a (blocking) semaphore to serialize access to the shared mem var, thus recreating the very problem you are trying to solve.
In other words, if non-blocking queries are crucial to you, you need to either request that this issue be solved by the PHP designers, or pick another mechanism to do your locking, one that already has this feature.
Just to clarify what is meant by "process" above:
On the Apache webserver, many PHP requests will be executed within the same process space because it is multithreaded. However, any semaphores got and acquired by a script and not released and removed will still be automatically cleaned up by the PHP interpreter each time the script terminates.
Remove any trash before emailing!
Note that when you reset $sem_identifier the semaphore won't block anymore!
This code does NOT work: 
  $key   = ftok(__FILE__,'m');
  $a    = sem_get($key);
  sem_acquire($a);
  $a = false;
while this one does: 
  $key   = ftok(__FILE__,'m');
  $a    = sem_get($key);
  sem_acquire($a);
  //$a = false;
So: use unique var names for your identifier!
In my tests sem_acquire() is 150 times faster than flock()
If you need non-blocking semaphores, here is an example how you may implement it. Use a shared memory variable to mark whether or not a lock exists and then use a semaphore around operations against that variable. I'll call my shared variable as 'token'.

When I execute this script in two parallel instances, I get the following output:
-------(first instance)----------------------------------------
... 482 begin try_lock()
... 482 acquire token semaphore
... 482   token semaphore acquired
... 482   token value: false
... 482   token new value: true
... 482 release token semaphore
... 482 acquire resource semaphore
... 482   resource semaphore acquired
... 482   access the resource for 4 sec
... 486 release resource semaphore
... 486 acquire token semaphore
... 486   token semaphore acquired
... 486   token value: true
... 486   token new value: false
... 486 release token semaphore
... 486 the end
-------(second instance)----------------------------------------
... 485 begin try_lock()
... 485 acquire token semaphore
... 485   token semaphore acquired
... 485   token value: true
... 485 release token semaphore
... 485 failed to acquire resource
... 485 wait for 1 sec
... 
... 486 wait for 1 sec
... 487 try again
... 487 begin try_lock()
... 487 acquire token semaphore
... 487   token semaphore acquired
... 487   token value: false
... 487   token new value: true
... 487 release token semaphore
... 487 acquire resource semaphore
... 487   resource semaphore acquired
... 487   access the resource for 4 sec
... 491 release resource semaphore
... 491 acquire token semaphore
... 491   token semaphore acquired
... 491   token value: true
... 491   token new value: false
... 491 release token semaphore
... 491 the end
Unfortunately, PHP does not currently support non-blocking semaphores.
If something like this is necessary you can utilize semaphores together with shared memory to create your own non-blocking lock mechanisms.
Use a shared memory variable to mark whether or not a lock exists and then use a semaphore around operations against that variable.

鹏仔微信 15129739599 鹏仔QQ344225443 鹏仔前端 pjxi.com 共享博客 sharedbk.com

免责声明:我们致力于保护作者版权,注重分享,当前被刊用文章因无法核实真实出处,未能及时与作者取得联系,或有版权异议的,请联系管理员,我们会立即处理! 部分文章是来自自研大数据AI进行生成,内容摘自(百度百科,百度知道,头条百科,中国民法典,刑法,牛津词典,新华词典,汉语词典,国家院校,科普平台)等数据,内容仅供学习参考,不准确地方联系删除处理!邮箱:344225443@qq.com)

图片声明:本站部分配图来自网络。本站只作为美观性配图使用,无任何非法侵犯第三方意图,一切解释权归图片著作权方,本站不承担任何责任。如有恶意碰瓷者,必当奉陪到底严惩不贷!

内容声明:本文中引用的各种信息及资料(包括但不限于文字、数据、图表及超链接等)均来源于该信息及资料的相关主体(包括但不限于公司、媒体、协会等机构)的官方网站或公开发表的信息。部分内容参考包括:(百度百科,百度知道,头条百科,中国民法典,刑法,牛津词典,新华词典,汉语词典,国家院校,科普平台)等数据,内容仅供参考使用,不准确地方联系删除处理!本站为非盈利性质站点,本着为中国教育事业出一份力,发布内容不收取任何费用也不接任何广告!)