The following information is provided as is, and the authors take no responsibility for the correctness.

Sagem GDI

Sagem GDI language is used in at least two MFU models by Ricoh: Aficio SP1000s and Aficio SP1100s. These devices include GDI 600dpi printers that are bundled with Windows driver only.

An easy way to investigate this format is to find a Windows box and print some documents “to file”.

Format description

The structure of the print job data:

Document header
Page1:
  Page header
  datablock1 datablock2 datablock3 ...
  Page footer
Page2:
  Page header
  datablock1 datablock2 datablock3 ...
  Page footer
...
PageN:
  Page header
  datablock1 datablock2 datablock3 ...
  Page footer
Document footer

As one can see the data is structured rather naturally and consists of pages divided into datablocks.

Document header

A static data of 83 bytes for any document: string ”) SAG-GDI RL;0;0;Comment Copyright Sagem Communication 2005. Version 1.0.0.0” followed by ”\r\n” followed by 0x1000 0200 0000 0000. To create it in python one would use

pack(
  '>76sbbHHI',
  ') SAG-GDI RL;0;0;Comment Copyright Sagem Communication 2005. Version 1.0.0.0',
  0x0D,0x0A,
  0x1000,0x0200,
  0
)

Page format

Page header

Page header carries information about page format and also number of copies to be made, paper type, paper position (paper tray selection) and toner economy control. It begins with “start page” command: 0x1100 0F00, then there comes the paper tray index (0x0000 0000 for “auto”, but its value doesn't seem to play any role at all for the mentioned Ricoh devices), then there follows some value 0x0404 0000 of an unknown purpose (using this static seems ok in every case), then page format width and height (double-bytes) measured in printer pixels (those “dots” that are in “dpi”), and then there come 5 bytes: index of the format (see formats table below), paper type (doesn't seem to have any effect in those Ricohs), number of copies, a zero, and 1 or 0 to switch toner economy on or off.

pack(
  '<II4H2B3B',
  0x000F0011,
  mediaposition,
  0x0404,0,paper_width,paper_height,
  format_index,mediatype,
  numcopies,0,toner_economy
)
Media types for Ricoh SP1000s/SP1100s
MediaType 0 Auto
MediaType 3 "Heavyweight"
Media position (input trays) for Ricoh SP1000s/SP1100s
InputSlot 0 Auto
InputSlot 1 "Automatic tray"
InputSlot 3 "Manual tray"
Paper formats for Ricoh SP1000s/SP1100s
  • A4
  Index: 0x0000
  Width: 0x129A
  Height: 0x1A7A
  Linefill: 0x9A4A
  • A5
  Index: 0x0004
  Width: 0x0CE2
  Height: 0x1276
  Linefill: 0xA233
  • A6
  Index: 0x000E
  Width: 0x08E9
  Height: 0x0CBE
  Linefill: 0xA923
  • Letter
  Index: 0x0001
  Width: 0x1324
  Height: 0x18DC
  Linefill: 0xA44C
  • Legal
  Index: 0x0002
  Width: 0x1324
  Height: 0x1FE4
  Linefill: 0xA44C
  • B5
  Index: 0x0005
  Width: 0x1006
  Height: 0x16CC
  Linefill: 0x8640
  • B6
  Index: 0x000D
  Width: 0x0B14
  Height: 0x0FE2
  Linefill: 0x942C
  • Monarch
  Index: 0x0008
  Width: 0x0850
  Height: 0x10A8
  Linefill: 0x9021

Width and Height are given in dots (those “dots” that are in “dpi”). For example, for A4 one has: 0x129A / 600 = 7.94” = 20.16cm - the width of A4 with narrow borders (hardware borders for the Ricohs mentioned above is ~3-4mm)

Linefill is explained below in Line format section.

Page datablock

Datablock header

Each datablock has a small header, that includes “start block” command 0x1200, the size of the upcoming block data in bytes (without the length of this header which is 6 bytes, only data length that follows) and a zero, for example, the following command is for the datablock of total length 0x70 = header length 0x06 + data length 0x6A

0x1200 6A00 0000

If offset of this “start block” command this 0x6B then the next “start block” command of the datablock that follows is expected at offset 0x6B + 6 + 0x6A = 0xDB

“Start block” in python:

pack('<3H',0x0012,block_data_size,0)

There is no any detected rule on how to divide data into datablocks, which involves also that the length of a datablock can be selected as one wishes. Successful tests (with those Ricohs) include datablock lengths up to 0xFF.

Datablock data

Print data is represented by lines. There is no special explicit command for starting and ending the line. Line end is given implicitly. Line is considered finished when the size of the data exceeds the Width of the page (see formats listing above). An importaint and not obvious behaviour here is that the last command is NOT splitted between lines independently of how many pixels it overflows the page Width, the last command is simply cropped at the right border of the page. If for example one wants to print out a page fully filled with black, he cannot do it with one long line - there must be given as many lines as Height of page for the given format (see formats listing above). If last pixel of the line is not black, one must fill the rest of the line with white pixels. According to previous note, this filling white pixels block can be of ANY width long enough to overflow the page Width and it also must be a single command - so it is ok (for simplicity) to use as many as Width white pixels for any line of data for any format.

There is no restriction found on how lines should be spead over datablocks. This means datablocks are more “blocks of commans” rather than “blocks of lines”. So one line can occupy more than one block, and the biggest block of length 0xFF can contain as many as 0xFF/2=127 lines (2 bytes is the shortest possible command for a line - a line filled with white/black). It is the complexity of the data that governs here.

Line format

Every line is considered as a sequence of segments with alternating colors white-black-white-black-white… etc. To describe this line one starts from the left side of the page and writes commands that correspond to these segments, so that the number of commands = number of segments. Each command (segment) is a 1- or 2-bytes sequence depending on the length of the segment. If color segment is less that 64 pixels long a single byte is used, if more that 64 the one has to use 2 bytes.

In the following command format consider binary representation of bytes: 0b00000000 (bits from 7 to 0 left to right). Introduce L1=segment_length%64, L2=segment_length/64, note L2=0 for segment_length<64.

first byte:

bit7: 0 if segment length < 64 (this means 1-byte command), 1 if segment length >= 64 (this means 2-byte command)
bit6: 0 for white, 1 for black segments
bits5-0: L1, maximum length of segment with 1-byte command is ''0b00111111 = 63''

second byte:

bits7-0: L2, maximum length of segment with 2-byte command is ''0b00111111 + 64 * 0b11111111 = 16383px''
         which is approx. 27" at 600dpi

examples:

  • Simple
0x5A = 0b01011010'' for black segment of length ''0b00011010 = 26px
  • Linefill

Linefill is the command for a completely white line, which is a frequently used command especially for text documents and documents with a lof of white space on pages. Take a Linefill from the formats table above for A4 and make sure it is really a white line of length equal to page Width.

''0x9A4A = 0b10011010 0b01001010''.

First bit = 1 ⇒ this is a 2-byte command, second bit is 0 ⇒ this is a white segment, its length is length = 0b00011010 + 64 * 0b01001010 = 0x129A = 4762px compare to A4 page Width value. All linefills in the above table are pre-calculated by this formula:

Linefill = (0x80 + Width % 64) << 8 + Width / 64
  • Assume one wants left half of A5 page black the other white. Width of A5 is 0x0CE2 = 3298. Half of it is 1649:
1649 = 64 * 25 + 49 = 64 * 0x19 + 0x31 = 64 * 0b00011001 + 0b00110001

Thus this will be a 2-byte command for both segments. First segment is black, second is white, one gets 4 bytes for the line:

0b11110001 0b00011001 0b10110001 0b00011001 = 0xF119 B119.

Note that the last command will be anyway cropped at the right end of the page so we could fearlessly use 0xA233 (a Linefill for A5, see table above) as the second command or any other which corresponds to a segment longer than a half of a page.

Page footer

A 6-bytes “end page” command: 0x1300 0000 0000. Python code:

pack('>3H',0x1300,0,0)

Document footer

A 6-bytes “end document” command: 0x1400 0000 0000. In python we write

pack('>3H',0x1400,0,0)

Remarks

This is not the absolutely full description of format, some static value might still be parameters, but they play secondary role as linux driver for Ricoh SP1000s and SP1100s works well based on this information.

 
formats/page_description_languages/sagem-gdi.txt · Last modified: 2011/03/18 04:09 (external edit)
 

All text is available under the terms of the GNU Free Documentation License (see Copyrights for details). Disclaimers

Recent changes RSS feed Powered by PHP Valid XHTML 1.0 Valid CSS Driven by DokuWiki