patch-2.4.4 linux/fs/ntfs/support.c
Next file: linux/fs/ntfs/support.h
Previous file: linux/fs/ntfs/super.h
Back to the patch index
Back to the overall index
- Lines: 395
- Date:
Wed Apr 18 11:49:13 2001
- Orig file:
v2.4.3/linux/fs/ntfs/support.c
- Orig date:
Tue Sep 5 14:07:30 2000
diff -u --recursive --new-file v2.4.3/linux/fs/ntfs/support.c linux/fs/ntfs/support.c
@@ -1,15 +1,10 @@
-/*
- * support.c
- * Specific support functions
+/* support.c - Specific support functions
*
* Copyright (C) 1997 Martin von Löwis
* Copyright (C) 1997 Régis Duchesne
- *
+ * Copyright (C) 2001 Anton Altaparmakov (AIA)
*/
-#ifdef HAVE_CONFIG_H
-#include "config.h"
-#endif
#include "ntfstypes.h"
#include "struct.h"
#include "support.h"
@@ -64,7 +59,7 @@
kfree(block);
}
#endif
-#else
+#else /* End of DEBUG functions. Normal ones below... */
void ntfs_debug(int mask, const char *fmt, ...)
{
}
@@ -102,7 +97,7 @@
memmove(dest, src, n);
}
-/* Warn that an error occured. */
+/* Warn that an error occurred. */
void ntfs_error(const char *fmt,...)
{
va_list ap;
@@ -120,68 +115,72 @@
ntfs_io io;
ntfs_debug(DEBUG_OTHER, "read_mft_record %x\n",mftno);
- if(mftno==FILE_MFT)
+ if(mftno == FILE_$Mft)
{
- ntfs_memcpy(buf,vol->mft,vol->mft_recordsize);
+ ntfs_memcpy(buf, vol->mft, vol->mft_recordsize);
return 0;
}
if(!vol->mft_ino)
{
- printk("ntfs:something is terribly wrong here\n");
- return ENODATA;
+ printk(KERN_ERR "NTFS: mft_ino is NULL. Something is terribly "
+ "wrong here!\n");
+ return -ENODATA;
}
- io.fn_put=ntfs_put;
- io.fn_get=0;
- io.param=buf;
- io.size=vol->mft_recordsize;
- error=ntfs_read_attr(vol->mft_ino,vol->at_data,NULL,
- mftno*vol->mft_recordsize,&io);
- if(error || (io.size!=vol->mft_recordsize))
+ io.fn_put = ntfs_put;
+ io.fn_get = 0;
+ io.param = buf;
+ io.size = vol->mft_recordsize;
+ error = ntfs_read_attr(vol->mft_ino, vol->at_data, NULL,
+ mftno * vol->mft_recordsize, &io);
+ if (error || (io.size != vol->mft_recordsize))
{
- ntfs_debug(DEBUG_OTHER, "read_mft_record: read %x failed (%d,%d,%d)\n",
- mftno,error,io.size,vol->mft_recordsize);
- return error?error:ENODATA;
+ ntfs_debug(DEBUG_OTHER, "read_mft_record: read %x failed "
+ "(%d,%d,%d)\n", mftno, error, io.size,
+ vol->mft_recordsize);
+ return error ? error : -ENODATA;
}
- ntfs_debug(DEBUG_OTHER, "read_mft_record: finished read %x\n",mftno);
- if(!ntfs_check_mft_record(vol,buf))
+ ntfs_debug(DEBUG_OTHER, "read_mft_record: finished read %x\n", mftno);
+ if(!ntfs_check_mft_record(vol, buf))
{
- printk("Invalid MFT record for %x\n",mftno);
- return EINVAL;
+ /* FIXME: This is incomplete behaviour. We might be able to
+ * recover at this stage. ntfs_check_mft_record() is too
+ * conservative at aborting it's operations. It is OK for
+ * now as we just can't handle some on disk structures
+ * this way. (AIA) */
+ printk(KERN_WARNING "NTFS: Invalid MFT record for %x\n", mftno);
+ return -EINVAL;
}
- ntfs_debug(DEBUG_OTHER, "read_mft_record: Done %x\n",mftno);
+ ntfs_debug(DEBUG_OTHER, "read_mft_record: Done %x\n", mftno);
return 0;
}
int ntfs_getput_clusters(ntfs_volume *vol, int cluster, ntfs_size_t start_offs,
- ntfs_io *buf)
+ ntfs_io *buf)
{
- struct super_block *sb=NTFS_SB(vol);
+ struct super_block *sb = NTFS_SB(vol);
struct buffer_head *bh;
ntfs_size_t to_copy;
- int length=buf->size;
- if(buf->do_read)
- ntfs_debug(DEBUG_OTHER, "get_clusters %d %d %d\n",cluster,start_offs,length);
- else
- ntfs_debug(DEBUG_OTHER, "put_clusters %d %d %d\n",cluster,start_offs,length);
- while(length)
- {
- if(!(bh=bread(sb->s_dev,cluster,vol->clustersize)))
- {
- ntfs_debug(DEBUG_OTHER, "%s failed\n", buf->do_read?"Reading":"Writing");
- return EIO;
+ int length = buf->size;
+
+ ntfs_debug(DEBUG_OTHER, "%s_clusters %d %d %d\n",
+ buf->do_read ? "get" : "put", cluster, start_offs, length);
+ while (length) {
+ if (!(bh = bread(sb->s_dev, cluster, vol->clustersize))) {
+ ntfs_debug(DEBUG_OTHER, "%s failed\n",
+ buf->do_read ? "Reading" : "Writing");
+ return -EIO;
}
- to_copy=min(vol->clustersize-start_offs,length);
+ to_copy = min(vol->clustersize - start_offs, length);
lock_buffer(bh);
- if(buf->do_read)
- buf->fn_put(buf,bh->b_data+start_offs,to_copy);
- else
- {
- buf->fn_get(bh->b_data+start_offs,buf,to_copy);
+ if (buf->do_read)
+ buf->fn_put(buf, bh->b_data + start_offs, to_copy);
+ else {
+ buf->fn_get(bh->b_data + start_offs, buf, to_copy);
mark_buffer_dirty(bh);
}
unlock_buffer(bh);
- length-=to_copy;
- start_offs=0;
+ length -= to_copy;
+ start_offs = 0;
cluster++;
brelse(bh);
}
@@ -193,152 +192,147 @@
return ntfs_unixutc2ntutc(CURRENT_TIME);
}
-/* when printing unicode characters base64, use this table.
- It is not strictly base64, but the Linux vfat encoding.
- base64 has the disadvantage of using the slash.
-*/
-static char uni2esc[64]=
- "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz+-";
-
-static unsigned char
-esc2uni(char c)
-{
- if(c<'0')return 255;
- if(c<='9')return c-'0';
- if(c<'A')return 255;
- if(c<='Z')return c-'A'+10;
- if(c<'a')return 255;
- if(c<='z')return c-'a'+36;
- if(c=='+')return 62;
- if(c=='-')return 63;
+/* When printing unicode characters base64, use this table. It is not strictly
+ * base64, but the Linux vfat encoding. base64 has the disadvantage of using
+ * the slash. */
+static char uni2esc[64] =
+ "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz+-";
+
+static unsigned char esc2uni(char c)
+{
+ if (c < '0') return 255;
+ if (c <= '9') return c - '0';
+ if (c < 'A') return 255;
+ if (c <= 'Z') return c - 'A' + 10;
+ if (c < 'a') return 255;
+ if (c <= 'z') return c - 'a' + 36;
+ if (c == '+') return 62;
+ if (c == '-') return 63;
return 255;
}
int ntfs_dupuni2map(ntfs_volume *vol, ntfs_u16 *in, int in_len, char **out,
- int *out_len)
+ int *out_len)
{
- int i,o,val,chl, chi;
- char *result,*buf,charbuf[NLS_MAX_CHARSET_SIZE];
- struct nls_table* nls=vol->nls_map;
-
- result=ntfs_malloc(in_len+1);
- if(!result)return ENOMEM;
- *out_len=in_len;
- result[in_len]='\0';
- for(i=o=0;i<in_len;i++){
- int cl,ch;
+ int i, o, val, chl, chi;
+ char *result, *buf, charbuf[NLS_MAX_CHARSET_SIZE];
+ struct nls_table* nls = vol->nls_map;
+
+ result = ntfs_malloc(in_len + 1);
+ if (!result)
+ return -ENOMEM;
+ *out_len = in_len;
+ result[in_len] = '\0';
+ for (i = o = 0; i < in_len; i++) {
+ int cl, ch;
/* FIXME: byte order? */
- cl=in[i] & 0xFF;
- ch=(in[i] >> 8) & 0xFF;
- if(!nls){
- if(!ch){
- result[o++]=cl;
+ cl = in[i] & 0xFF;
+ ch = (in[i] >> 8) & 0xFF;
+ if (!nls) {
+ if (!ch) {
+ result[o++] = cl;
continue;
}
- }else{
+ } else {
/* FIXME: byte order? */
wchar_t uni = in[i];
- if ( (chl = nls->uni2char(uni, charbuf, NLS_MAX_CHARSET_SIZE)) > 0){
+ if ((chl = nls->uni2char(uni, charbuf,
+ NLS_MAX_CHARSET_SIZE)) > 0) {
/* adjust result buffer */
- if (chl > 1){
- buf=ntfs_malloc(*out_len + chl - 1);
+ if (chl > 1) {
+ buf = ntfs_malloc(*out_len + chl - 1);
memcpy(buf, result, o);
ntfs_free(result);
- result=buf;
- *out_len+=(chl-1);
+ result = buf;
+ *out_len += (chl - 1);
}
- for (chi=0;chi<chl;chi++)
+ for (chi = 0; chi < chl; chi++)
result[o++] = charbuf[chi];
} else
result[o++] = '?';
continue;
-
}
- if(!(vol->nct & nct_uni_xlate))goto inval;
+ if (!(vol->nct & nct_uni_xlate))
+ goto inval;
/* realloc */
- buf=ntfs_malloc(*out_len+3);
- if( !buf ) {
- ntfs_free( result );
- return ENOMEM;
+ buf = ntfs_malloc(*out_len + 3);
+ if (!buf) {
+ ntfs_free(result);
+ return -ENOMEM;
}
- memcpy(buf,result,o);
+ memcpy(buf, result, o);
ntfs_free(result);
- result=buf;
- *out_len+=3;
- result[o++]=':';
- if(vol->nct & nct_uni_xlate_vfat){
- val=(cl<<8)+ch;
- result[o+2]=uni2esc[val & 0x3f];
- val>>=6;
- result[o+1]=uni2esc[val & 0x3f];
- val>>=6;
- result[o]=uni2esc[val & 0x3f];
- o+=3;
- }else{
- val=(ch<<8)+cl;
- result[o++]=uni2esc[val & 0x3f];
- val>>=6;
- result[o++]=uni2esc[val & 0x3f];
- val>>=6;
- result[o++]=uni2esc[val & 0x3f];
+ result = buf;
+ *out_len += 3;
+ result[o++] = ':';
+ if (vol->nct & nct_uni_xlate_vfat) {
+ val = (cl << 8) + ch;
+ result[o+2] = uni2esc[val & 0x3f];
+ val >>= 6;
+ result[o+1] = uni2esc[val & 0x3f];
+ val >>= 6;
+ result[o] = uni2esc[val & 0x3f];
+ o += 3;
+ } else {
+ val = (ch << 8) + cl;
+ result[o++] = uni2esc[val & 0x3f];
+ val >>= 6;
+ result[o++] = uni2esc[val & 0x3f];
+ val >>= 6;
+ result[o++] = uni2esc[val & 0x3f];
}
}
- *out=result;
+ *out = result;
return 0;
inval:
ntfs_free(result);
- *out=0;
- return EILSEQ;
+ *out = 0;
+ return -EILSEQ;
}
int ntfs_dupmap2uni(ntfs_volume *vol, char* in, int in_len, ntfs_u16 **out,
- int *out_len)
+ int *out_len)
{
- int i,o;
+ int i, o;
ntfs_u16* result;
- struct nls_table* nls=vol->nls_map;
+ struct nls_table* nls = vol->nls_map;
- *out=result=ntfs_malloc(2*in_len);
- if(!result)return ENOMEM;
- *out_len=in_len;
- for(i=o=0;i<in_len;i++,o++){
+ *out=result = ntfs_malloc(2 * in_len);
+ if (!result)
+ return -ENOMEM;
+ *out_len = in_len;
+ for (i = o = 0; i < in_len; i++, o++){
wchar_t uni;
- if(in[i]!=':' || (vol->nct & nct_uni_xlate)==0){
+ if (in[i] != ':' || (vol->nct & nct_uni_xlate) == 0){
int charlen;
- /* FIXME: is this error handling ok? */
charlen = nls->char2uni(&in[i], in_len-i, &uni);
if (charlen < 0)
return charlen;
- *out_len -= (charlen-1);
- i += (charlen-1);
- }else{
- unsigned char c1,c2,c3;
- *out_len-=3;
- c1=esc2uni(in[++i]);
- c2=esc2uni(in[++i]);
- c3=esc2uni(in[++i]);
- if(c1==255 || c2==255 || c3==255)
+ *out_len -= (charlen - 1);
+ i += (charlen - 1);
+ } else {
+ unsigned char c1, c2, c3;
+ *out_len -= 3;
+ c1 = esc2uni(in[++i]);
+ c2 = esc2uni(in[++i]);
+ c3 = esc2uni(in[++i]);
+ if (c1 == 255 || c2 == 255 || c3 == 255)
uni = 0;
- else if(vol->nct & nct_uni_xlate_vfat){
+ else if (vol->nct & nct_uni_xlate_vfat) {
uni = (((c2 & 0x3) << 6) + c3) << 8 |
- ((c1 << 4) + (c2 >> 2));
- }else{
+ ((c1 << 4) + (c2 >> 2));
+ } else {
uni = ((c3 << 4) + (c2 >> 2)) << 8 |
- (((c2 & 0x3) << 6) + c1);
+ (((c2 & 0x3) << 6) + c1);
}
}
/* FIXME: byte order? */
result[o] = uni;
- if(!result[o]){
+ if (!result[o]) {
ntfs_free(result);
- return EILSEQ;
+ return -EILSEQ;
}
}
return 0;
}
-/*
- * Local variables:
- * c-file-style: "linux"
- * End:
- */
FUNET's LINUX-ADM group, linux-adm@nic.funet.fi
TCL-scripts by Sam Shen (who was at: slshen@lbl.gov)