Làm cách nào để xuất tập tin từ phần bù được chỉ định, nhưng không phải là dd dd bs = 1 Skip = N mệnh?


28

Làm thế nào để làm điều tương tự dd if=somefile bs=1 skip=1337 count=31337000, nhưng hiệu quả, không sử dụng đọc và ghi không 1 byte?

Giải pháp được mong đợi:

  1. Để đơn giản (đối với người không đơn giản tôi có thể viết một số Perl oneliner sẽ làm điều này)
  2. Để hỗ trợ các khoản bù đắp và độ dài lớn (vì vậy, các bản hack có kích thước khối trong dd sẽ không trợ giúp)

Giải pháp từng phần (không đủ đơn giản, thử tương tự với độ dài sẽ khiến nó thậm chí còn phức tạp hơn):

dd if=somefile bs=1000 skip=1 count=31337 | { dd bs=337 count=1 of=/dev/null; rest_of_pipeline; }
# 1337 div 1000 and 1337 mod 1000

Bạn đang cố gắng thay đổi kích thước khối mà dd đang sử dụng?
cmorse

Thay đổi khối kích thước => thay đổi đơn vị bỏ qua và đếm
Vi.

Câu trả lời:


37

Điều này sẽ làm điều đó (trên gnu dd):

dd if=somefile bs=4096 skip=1337 count=31337000 iflag=skip_bytes,count_bytes

Trong trường hợp bạn đang sử dụng seek=là tốt, bạn cũng có thể xem xét oflag=seek_bytes.

Từ info dd:

`count_bytes'
      Interpret the `count=' operand as a byte count, rather than a
      block count, which allows specifying a length that is not a
      multiple of the I/O block size.  This flag can be used only
      with `iflag'.

`skip_bytes'
      Interpret the `skip=' operand as a byte count, rather than a
      block count, which allows specifying an offset that is not a
      multiple of the I/O block size.  This flag can be used only
      with `iflag'.

`seek_bytes'
      Interpret the `seek=' operand as a byte count, rather than a
      block count, which allows specifying an offset that is not a
      multiple of the I/O block size.  This flag can be used only
      with `oflag'.

Ps: Tôi hiểu câu hỏi này đã cũ và có vẻ như những lá cờ này đã được triển khai sau khi câu hỏi ban đầu được hỏi, nhưng vì đây là một trong những kết quả google đầu tiên cho một tìm kiếm dd liên quan mà tôi đã làm, mặc dù vậy sẽ rất tốt để cập nhật với cái mới đặc tính.


2

Sử dụng một quy trình để bỏ tất cả các byte ban đầu, sau đó một giây để đọc các byte thực tế, ví dụ:

echo Hello, World\! | ( dd of=/dev/null bs=7 count=1 ; dd bs=5 count=1 )

Thứ hai ddcó thể đọc đầu vào với bất kỳ khối nào bạn thấy hiệu quả. Lưu ý rằng điều này đòi hỏi một quá trình bổ sung để được sinh ra; tùy thuộc vào hệ điều hành của bạn sẽ phải chịu chi phí, nhưng có lẽ nhỏ hơn việc phải đọc từng tệp một byte (trừ khi bạn có một tệp rất nhỏ, trong trường hợp đó sẽ không có vấn đề gì).


Nó có hoạt động tốt không (ví dụ như không có quá nhiều bộ nhớ) cho các khoản bù và số lượng lớn? dd if=/dev/sda bs=10000000001 | dd bs=255 count=1 | hd-> "dd: số không hợp lệ` 10000000001 '"
Vi.

@Vi. Nếu bạn muốn bỏ qua một phần bù lớn thì bạn nên đọc lần đầu dưới dạng một chuỗi các khối có kích thước "lý tưởng" (tùy theo nguồn của bạn) (16M), sau đó thả một loạt các khối có kích thước nhỏ hơn (512) sẽ có trong bộ nhớ , để "phóng to" dữ liệu của bạn, trước khi bạn bỏ một phần lẻ không phù hợp với kích thước khối (bs = 1 bên dưới) và sau đó đọc khối bạn muốn. Ví dụ: bạn muốn đọc 255 byte từ offset 10000000001: dd if=/dev/sda bs=16M skip=596 count=1 | dd bs=512 skip=1522 count=1 | (dd bs=1 count=1 of=/dev/null ; dd bs=255 count=1)
RolKau

Chắc chắn sẽ dễ sử dụng hơn read -nđể bỏ qua? Rồi tính sau head -c? Ví dụ: cat somefile | (read -n 1337; head -c 31337000)Hoặc bạn có thể làm điều đó mà không cần sinh ra một quy trình bổ sung:exec 3<somefile; read -n 1337 -u 3; head -c 31337000 <&3
Gannet

1

Thay vì bs=1sử dụng bs=4096hoặc nhiều hơn.


2
Sau đó, nó sẽ đọc từ offset 1337 * 4096 thay vì 1337
Vi.

1
Aha, tôi hiểu rồi, có lẽ sẽ dễ dàng hơn để viết một tập lệnh Python đơn giản, ví dụ như trong ví dụ này stackoverflow.com/questions/1035340/ trên với f.seek(1337)trước khi sử dụngread(MY_CHUNK_SIZE)
ccpizza

Cảm giác như cách đáng tin cậy nhất có lẽ là viết một tệp thực thi tùy chỉnh. Một số hệ thống không có Python, hoặc Ruby hoặc thậm chí Perl. : |
Trejkaz

1

Bạn có thể thử lệnh hexdump:

hexdump  -v <File Path> -c -n <No of bytes to read> -s <Start Offset>

Nếu bạn chỉ muốn xem nội dung:

#/usr/bin/hexdump -v -C mycorefile -n 100 -s 100
00000064 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 |................| 
00000074 00 00 00 00 01 00 00 00 05 00 00 00 00 10 03 00 |................| 
00000084 00 00 00 00 00 00 40 00 00 00 00 00 00 00 00 00 |......@.........| 
00000094 00 00 00 00 00 00 00 00 00 00 00 00 00 a0 03 00 |................| 
000000a4 00 00 00 00 00 10 00 00 00 00 00 00 01 00 00 00 |................| 
000000b4 06 00 00 00 00 10 03 00 00 00 00 00 00 90 63 00 |..............c.| 
000000c4 00 00 00 00 |....| 
000000c8 #

Đây không phải là về việc xem tập tin dưới dạng hex. Đó là về việc trích xuất nội dung của một tệp (ví dụ để sao chép nó ở đâu đó) từ phần bù được chỉ định theo byte.
Vi.
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.