[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[FDclone-users:00510] Re: FDclone でファイルサイズが 0 と表示される



 しらいです。

In Message-Id <OF952D75F3.35BEAB51-ON4925715A.000C3CE6@tky.lightwell.co.jp>
        SHIOTA Shoichi <Shoichi.Shiota@lightwell.co.jp>さんwrites:
> 潮田です。

> 1 [0]
> 2 [0]
> 3 [2147483647]
> 4 [2147483647][0][2000e832]
> 5 [2147483647][0][0]
> 7 [2147483647][0][0]
> 
> 何かの参考になれば良いのですが。

 頭のところで [0] になってるのが今回の支障の元凶です。ここ
で期待されている値は 0xffffffff 即ち 4294967295 なんです。
 実際は、この値を右に -32 回シフトしているのですが、多くの
CPU では負数回のシフトは 0 回のシフトと同じなので元の値のま
まになるんですが、AIX では 2147483648 - 32 回シフトして、そ
の結果 0 になっているようですね。


> >  理屈はともかく、そういう特性を鑑みて [FDclone-users:00495]
> > の patch を作り直すとこんな感じになるんじゃないでしょうか?
> これは、素の FD-2.08b に適用して変化をみれば良いのですよね。
> 残念ながら変化が無いようにみえます。

 んー、おかしいですねー。ちょっと patch を作り直してみたの
で、今度のはどうでしょう?


> いまさら火に油を注ぐような報告で、心苦しいのですが、
> tar ファイル中の、サイズや日付がおかしいのは、ファイルサイズが
> 大きいから(だけ)ではなさそうです。

 支障の原因はサイズ値そのものではなくてサイズを示す桁数にあ
りますから、大きなサイズでなくても同じ症状になると思います。
 ただ、直ったことを確認するためにはやはり大きなサイズでの挙
動も見ておく必要があるので、4GB 超のファイルがどう表示される
かの検証は必要だと思います。


> つなり小さなサイズでも同じで、サイズは 0 、日付は実行した
> 年の 1/1 00:00 と表示されているようです。

 あそこで break で終わっているということはエラー扱いなんで
すよ。エラーなので、そのカラム以降の情報は読み飛ばしてしまっ
て、それで日付が狂ってるのかと。
 なので、サイズさえ正しく取得出来れば後は大丈夫だと思います。

---- Cut Here ----
diff -u ../old/FD-2.08b/parse.c ./parse.c
--- ../old/FD-2.08b/parse.c	Thu Mar 30 00:00:00 2006
+++ ./parse.c	Sat Apr 22 03:00:55 2006
@@ -256,8 +256,9 @@
 			break;
 		}
 
-		mask = (MAXUTYPE(u_long_t)
-			>> (((int)sizeof(long_t) - len) * BITSPERBYTE));
+		mask = MAXUTYPE(u_long_t);
+		if (len < (int)sizeof(u_long_t))
+			mask >>= ((int)sizeof(u_long_t) - len) * BITSPERBYTE;
 		if (flags & VF_UNSIGNED) {
 			if (u & ~mask) {
 				s = NULL;
@@ -274,6 +275,27 @@
 			memcpy(&u, &n, sizeof(u));
 		}
 
+#ifndef	HAVELONGLONG
+		if (len > (int)sizeof(u_long_t)) {
+			char *buf;
+			u_long_t tmp;
+			int hi;
+
+			hi = 0;
+			if (!(flags & VF_UNSIGNED)) {
+				mask = (MAXUTYPE(u_long_t) >> 1);
+				if (u & ~mask) hi = 0xff;
+			}
+			buf = va_arg(args, char *);
+			memset(buf, hi, len);
+
+			tmp = 0x5a;
+			cp = (char *)(&tmp);
+			if (*cp != 0x5a) buf += len - sizeof(u_long_t);
+			memcpy(buf, (char *)(&u), sizeof(u));
+		}
+		else
+#endif	/* !HAVELONGLONG */
 		if (len == (int)sizeof(u_long_t))
 			*(va_arg(args, u_long_t *)) = u;
 #ifdef	HAVELONGLONG
diff -u ../old/FD-2.08b/printf.c ./printf.c
--- ../old/FD-2.08b/printf.c	Thu Mar 30 00:00:00 2006
+++ ./printf.c	Sat Apr 22 03:05:34 2006
@@ -496,29 +496,37 @@
 		}
 
 		if (base) {
-			if (len == (int)sizeof(u_long_t))
-				u = va_arg(args, u_long_t);
-#ifdef	HAVELONGLONG
-			else if (len == (int)sizeof(u_long))
-				u = va_arg(args, u_long);
-#endif
-			else u = va_arg(args, u_int);
-
 #ifndef	HAVELONGLONG
 			if (len > (int)sizeof(u_long_t)) {
-				u_long_t hi, tmp;
-
-				while (len > (int)sizeof(u_int)) {
-					hi = va_arg(args, u_int);
-					len -= (int)sizeof(u_int);
-				}
+				u_long_t tmp;
+				int hi;
 
+# ifndef	HPUX
+	/*
+	 * HP-UX always pushes arguments from lowest to uppermost,
+	 * in spite of the CPU endien.
+	 */
 				tmp = 0x5a;
 				cp = (char *)(&tmp);
 				if (*cp != 0x5a) {
-					tmp = hi;
-					hi = u;
-					u = tmp;
+					hi = va_arg(args, u_int);
+					len -= (int)sizeof(u_int);
+					while (len > (int)sizeof(u_long_t)) {
+						tmp = va_arg(args, u_int);
+						len -= (int)sizeof(u_int);
+					}
+					u = va_arg(args, u_long_t);
+				}
+				else
+# endif	/* !HPUX */
+				{
+					hi = 0;
+					u = va_arg(args, u_long_t);
+					len -= (int)sizeof(u_long_t);
+					while (len > 0) {
+						hi = va_arg(args, u_int);
+						len -= (int)sizeof(u_int);
+					}
 				}
 
 				if (pbufp -> flags & VF_UNSIGNED) {
@@ -526,7 +534,7 @@
 				}
 				else {
 					mask = (MAXUTYPE(u_long_t) >> 1);
-					if (hi & ~mask) {
+					if (hi < 0) {
 						if (++hi || !(u & ~mask))
 							u = ~mask;
 					}
@@ -538,10 +546,20 @@
 			}
 			else
 #endif	/* !HAVELONGLONG */
+			if (len == (int)sizeof(u_long_t))
+				u = va_arg(args, u_long_t);
+#ifdef	HAVELONGLONG
+			else if (len == (int)sizeof(u_long))
+				u = va_arg(args, u_long);
+#endif
+			else u = va_arg(args, u_int);
+
 			if (!(pbufp -> flags & VF_UNSIGNED)) {
-				mask = (MAXUTYPE(u_long_t)
-					>> (((int)sizeof(long_t) - len)
-					* BITSPERBYTE + 1));
+				mask = MAXUTYPE(u_long_t);
+				if (len < (int)sizeof(u_long_t))
+					mask >>= ((int)sizeof(u_long_t) - len)
+						* BITSPERBYTE;
+				mask >>= 1;
 				if (u & ~mask) u |= ~mask;
 			}
 			len = setint(u, base, pbufp, width, prec);
---- Cut Here ----

                                               しらい たかし