トップ «前の日(06-17) 最新 次の日(06-19)» 追記

Masa's blog

検索キーワード:

2009年06月18日 request_module[net-pf-10]: waitpid(3788,...) failed, errno 1 (その6)

_ request_module[net-pf-10]: waitpid(3788,...) failed, errno 1 (その6)

request_module[net-pf-10]: waitpid(3788,...) failed, errno 1

の errno 1 は /usr/include/asm/errno.h より

#define EPERM            1      /* Operation not permitted */

を表していると思っていた。ところが /usr/src/linux/kernel/kmod.c より

  178  int request_module(const char * module_name)
  179  {
  180          pid_t pid;
  181          int waitpid_result;
  182          sigset_t tmpsig;
  183          int i;
  184          static atomic_t kmod_concurrent = ATOMIC_INIT(0);
  185  #define MAX_KMOD_CONCURRENT 50  /* Completely arbitrary value - KAO */
  186          static int kmod_loop_msg;
  187
  188          /* Don't allow request_module() before the root fs is mounted!  */
  189          if ( ! current->fs->root ) {
  190                  printk(KERN_ERR "request_module[%s]: Root fs not mounted\n",
  191                          module_name);
  192                  return -EPERM;
  193          }
  194
  195          /* If modprobe needs a service that is in a module, we get a recursive
  196           * loop.  Limit the number of running kmod threads to max_threads/2 or
  197           * MAX_KMOD_CONCURRENT, whichever is the smaller.  A cleaner method
  198           * would be to run the parents of this process, counting how many times
  199           * kmod was invoked.  That would mean accessing the internals of the
  200           * process tables to get the command line, proc_pid_cmdline is static
  201           * and it is not worth changing the proc code just to handle this case.
  202           * KAO.
  203           */
  204          i = max_threads/2;
  205          if (i > MAX_KMOD_CONCURRENT)
  206                  i = MAX_KMOD_CONCURRENT;
  207          atomic_inc(&kmod_concurrent);
  208          if (atomic_read(&kmod_concurrent) > i) {
  209                  if (kmod_loop_msg++ < 5)
  210                          printk(KERN_ERR
  211                                 "kmod: runaway modprobe loop assumed and stopped\n");
  212                  atomic_dec(&kmod_concurrent);
  213                  return -ENOMEM;
  214          }
  215
  216          pid = kernel_thread(exec_modprobe, (void*) module_name, 0);
  217          if (pid < 0) {
  218                  printk(KERN_ERR "request_module[%s]: fork failed, errno %d\n", module_name, -pid);
  219                  atomic_dec(&kmod_concurrent);
  220                  return pid;
  221          }
  222
  223          /* Block everything but SIGKILL/SIGSTOP */
  224          spin_lock_irq(&current->sigmask_lock);
  225          tmpsig = current->blocked;
  226          siginitsetinv(&current->blocked, sigmask(SIGKILL) | sigmask(SIGSTOP));
  227          recalc_sigpending(current);
  228          spin_unlock_irq(&current->sigmask_lock);
  229
  230          waitpid_result = waitpid(pid, NULL, __WCLONE);
  231          atomic_dec(&kmod_concurrent);
  232
  233          /* Allow signals again.. */
  234          spin_lock_irq(&current->sigmask_lock);
  235          current->blocked = tmpsig;
  236          recalc_sigpending(current);
  237          spin_unlock_irq(&current->sigmask_lock);
  238
  239          if (waitpid_result != pid) {
  240                  printk(KERN_ERR "request_module[%s]: waitpid(%d,...) failed, errno %d\n",
  241                         module_name, pid, -waitpid_result);
  242          }
  243          return 0;
  244  }

240行〜241行が問題のエラーメッセージを出しているところなのだが、errnoに該当するのは -waitpid_result で、これは230行の waitpidのリターン値(-1)を符号反転したものに過ぎない。waitpidのリターン値が-1なのは単に「エラーで返ったよ」の印に過ぎず、真のエラーコードは errno に格納されているはず。なので、

  239          if (waitpid_result != pid) {
  240  #if 0
  241                  printk(KERN_ERR "request_module[%s]: waitpid(%d,...) failed, errno %d\n",
  242                         module_name, pid, -waitpid_result);
  243  #else
  244                  printk(KERN_ERR "request_module[%s]: waitpid(%d,...) failed, errno %d realerrno %d\n",
  245                         module_name, pid, -waitpid_result, errno);
  246  #endif
  247          }

のようにして、カーネルをビルド中。

_ request_module[net-pf-10]: waitpid(3788,...) failed, errno 1 (その7)

本当の errno は

ECHILD 10 /* No child processes */

だった。

2.4系のスレッドの問題かもしれないが、はっきりとした事は言えない。とりあず

*** kernel/kmod.c.ORG   2009-06-18 01:09:00.000000000 +0900
--- kernel/kmod.c       2009-06-18 09:56:55.000000000 +0900
***************
*** 237,244 ****
--- 237,251 ----
        spin_unlock_irq(&current->sigmask_lock);

        if (waitpid_result != pid) {
+ #if 0
                printk(KERN_ERR "request_module[%s]: waitpid(%d,...) failed, errno %d\n",
                       module_name, pid, -waitpid_result);
+ #else
+               if (errno != ECHILD){
+                       printk(KERN_ERR "request_module[%s]: waitpid(%d,...) failed, errno %d realerrno %d\n",
+                              module_name, pid, -waitpid_result, errno);
+               }
+ #endif
        }
        return 0;
  }

みたいにして、ECHILDの時はメッセージを出さないようにした。ビルド&再起動して様子をみているけれど、非常に場当たり的だが問題なさそう。


2023年06月18日 mplayerでdvd-videoをメニュー再生およびマウス操作する方法

mplayer -mouse-movements  dvdnav:// -dvd-device /dev/dvd1

_ powershellでPUA、サロゲートペア、IVSを含んだ文字列を操作するサンプル

StringSample.ps1

function getLength($string){
	$count = 0
	for ($i = 0; $i -lt $s.length; $i++){
		if ([int][char]$s[$i] -ge 0xd800 -and [int][char]$s[$i] -le 0xdbff){
			if ([int][char]$s[$i] -eq 0xdb40){
#				IVS H
			}else{
#				SURR H
				$count++
			}
		}elseif ([int][char]$s[$i] -ge 0xdc00 -and [int][char]$s[$i] -le 0xdfff){
			if ([int][char]$s[$i] -ge 0xdd00 -and [int][char]$s[$i] -le 0xddef){
#				IVS L
			}else{
#				SURR L
			}
		}else{
#			BMP
			$count++
		}
	}
	return $count
}

function getCharByIndex($string, $index){
	$out = ""
	$windex = -1
	for ($i = 0; $i -lt $s.length; $i++){
		if ([int][char]$s[$i] -ge 0xd800 -and [int][char]$s[$i] -le 0xdbff){
			if ([int][char]$s[$i] -eq 0xdb40){
#				IVS H
			}else{
#				SURR H
				$windex++
			}
		}elseif ([int][char]$s[$i] -ge 0xdc00 -and [int][char]$s[$i] -le 0xdfff){
			if ([int][char]$s[$i] -ge 0xdd00 -and [int][char]$s[$i] -le 0xddef){
#				IVS L
			}else{
#				SURR L
			}
		}else{
#			BMP
			$windex++
		}
		if ($windex -eq $index){
			$out = $s[$i]
			if ([int][char]$s[$i] -ge 0xd800 -and [int][char]$s[$i] -le 0xdbff){
				if ([int][char]$s[$i] -eq 0xdb40){
#					IVS H
				}else{
#					SURR H
					$i++
					$out += $s[$i]	# add SURR L
				}
			}
			if ([int][char]$s[$i + 1] -eq 0xdb40){
#				IVS H
				$i++
				$out += $s[$i]	# add IVS H
				$i++
				$out += $s[$i]	# add IVS L
			}
		}
	}
	return $out
}

function getSubString($string, $index, $length){
	$out = ""
	for ($i = $index; $i -lt ($index + $length); $i++){
		$out += (getCharByIndex $string $i)
	}
	return $out
}

$s = "a漢𠮷辻󠄀b"
echo ("文字列:" + $s)
echo ("文字数:" + (getLength $s))
echo ("0文字目:" + (getCharByIndex $s 0))
echo ("1文字目(BMP):" + (getCharByIndex $s 1))
echo ("2文字目(PUA):" + (getCharByIndex $s 2))
echo ("3文字目(surrogate):" + (getCharByIndex $s 3))
echo ("4文字目(BMP+IVS):" + (getCharByIndex $s 4))
echo ("2文字目から3文字分:" + (getSubString $s 2 3))

実行結果

PS C:\Users\USER\Desktop\PowerShell> .\SampleString.ps1
文字列:a漢𠮷辻󠄀b
文字数:6
0文字目:a
1文字目(BMP):漢
2文字目(PUA):
3文字目(surrogate):𠮷
4文字目(BMP+IVS):辻󠄀
2文字目から3文字分:𠮷辻󠄀
PS C:\Users\USER\Desktop\PowerShell>