firmware update
Dan Williams
dcbw at redhat.com
Mon Dec 14 10:00:38 PST 2015
On Mon, 2015-12-14 at 11:44 -0600, Dan Williams wrote:
> On Mon, 2015-12-14 at 14:15 +0100, Bjørn Mork wrote:
> > Aleksander Morgado <aleksander at aleksander.es> writes:
> >
> > > On Mon, Dec 14, 2015 at 10:12 AM, dailijin <dailijin126 at 126.com>
> > > wrote:
> > > > Thanks your quick responds, this is bad news to me.
> > > >
> > > > I known the Sierra firmware updater worked with GobiNet and
> > > > GobiSerial
> > > > driver, but the two driver will conflict with libqmi driver,
> > > > this
> > > > is indeed
> > > > not convenience for my dialing logic. Do you have planed to
> > > > support this
> > > > feature in libqmi?
> > >
> > > Well, it's not much about libqmi itself, but about rewriting an
> > > updater program that plays nicely with qmi_wwan and the upstream
> > > serial drivers, e.g. using libqmi/qmicli to reboot into QDL
> > > download
> > > mode and then using an improved "gobi_loader" program to load the
> > > new
> > > firmware via the exposed TTY.
> >
> > It seems simple to implement on paper, but there are a few issues
> > to
> > keep in mind:
> >
> > - It's very easy to end up with a (soft-)bricked device if anything
> > unexpected happens. And we don't know what to expect in
> > general...
> > - There are no public docs of any of the involved protocols, which
> > makes
> > it difficult to recover from a soft brick
> > - We don't know how to properly sanity check and verify the images.
> > We
> > can only upload what we have and hope for the best
> >
> >
> > I have never tried this procedure, so be careful and read the above
> > once
> > or twice before you try it, but the procedure seems to be:
> >
>
> See also gobi-api/GobiAPI_1.0.40/Core/QDLBuffers.[cpp|h], gobi
> -api/GobiAPI_1.0.40/Core/QDLEnum.h, and gobi
> -api/GobiAPI_1.0.40/Core/QDLProtocolServer.cpp in libqmi repo.
> Qualcomm released most of this in the GobiAPI drops. Not sure what
> Sierra modified, but it looks mostly the same.
>
> > a) several rounds of model and version checking using
> >
> > DMS "Get Model" (0x0022)
> > DMS "Sierra Wireless Get Model???" (0x5556) [1]
> > DMS "Get Revision" (0x0023)
> >
> > I guess this part can be ignored wrt image writing, but proper
> > download code should verify that the image file matches the
> > modem,
> > both wrt hardware and currently running version. We don't know
> > if
> > downgrades are supported, so let's assume the are not.
> >
> >
> > b) switch to QDL mode using DMS ??? (0x003e). This is a request
> > with
> > no
> > TLVs, and the reply has only TLV 0x02:
>
> That would be eQMI_DMS_SET_FIRMWARE_ID where the only applicable TLV
> (0x01) is a 32-bit firmware ID. Clearly in your trace the device
> isn't
> sending that TLV.
>
> > < 01 0C 00 00 02 02 00 09 00 3E 00 00 00
> > > 01 13 00 80 02 02 02 09 00 3E 00 07 00 02 04 00 00 00 00 00
>
> The reply should be a result code consisting of the 16-bit status and
> a
> 16-bit code. Which matches your trace; there is no error.
>
> > It is followed by an immediate reboot to "QDL mode"
>
> So perhaps SetFirmwareID with no TLV is the "reboot to QDL mode"
> trigger.
>
> >
> > c) When in QDL mode, I believe you start out in a protocol known as
> > "DLOAD" or "DMSS Download Protocol" [2]. The first thing you do
> > there
> > is to switch to another protocl, known as "Streaming DLOAD" or
> > "SDP"
> > [3].
>
> Some bits in GobiAPI might be related, but it looks like they take
> effect after the initial "Hello" packet:
>
> ePROTOCOL_QDL_RX, // 09 QDL variant of streaming protocol
> (incoming)
> ePROTOCOL_QDL_TX, // 10 QDL variant of streaming protocol
> (outgoing)
Actually it looks like these are just used internally, so they are not
relevant to the actual protocol.
Dan
> There are also the buffer definitions for "unframed" requests, which
> makes sense WRT streaming since unframed would mean dropping the HDLC
> framing.
>
> > I have yet to find any docs of this switching request, but
> > snooping
> > shows that it is this simple HDLC frame:
> >
> > 7e 70 00 00 14 46 7e
> >
> > The "00 00" is a command parameter. I have no idea of the exact
> > meaning. I've only observed a 0 so far.
>
> That part is odd, haven't found anything interesting about it. The
> QCDM 0x70 command is DIAG_CMD_RAM_RW (but references calibration RAM)
> so that's probably not anything related.
>
> >
> > d) SDP is what the gobi-loader [4] speaks. It starts with a
> > semi-doumented hello request (0x01) and ack (0x02):
> >
> > 0040 7e 01 51 43 4f 4d 20 68 69 67 68 20 73 70 65 65 ~.QCOM high
> > spee
> > 0050 64 20 70 72 6f 74 6f 63 6f 6c 20 68 73 74 00 00 d protocol
> > hst..
> > 0060 00 00 06 06 30 00 00 00 de d3 7e
> > ....0.....~
> >
> > 0040 7e 02 51 43 4f 4d 20 68 69 67 68 20 73 70 65 65 ~.QCOM high
> > spee
> > 0050 64 20 70 72 6f 74 6f 63 6f 6c 20 74 67 74 30 00 d protocol
> > tgt0.
> > 0060 00 00 06 06 00 00 00 00 00 00 00 00 00 00 00 00
> > ................
> > 0070 00 30 d9 bc 7e .0..~
>
> See sQDLHello::BuildHelloReq():
>
> struct sQDLRawHelloReq {
> BYTE mCommandCode; (eQDL_CMD_HELLO_REQ = 0x01)
> BYTE mMagicNumber[32]; (QCOM high speed protocol)
> BYTE mMaxVersion; (QDL_MIN_VERSION = 0x06)
> BYTE mMinVersion; (QDL_MAX_VERSION = 0x06)
> BYTE mFeatures; (QDL_FEATURE_GENERIC_UNFRAMED/0x10 |
> QDL_FEATURE_QDL_UNFRAMED/0x20 = 0x30)
> };
>
> struct sQDLRawHelloRsp {
> BYTE mCommandCode; (eQDL_CMD_HELLO_RSP = 0x02)
> BYTE mMagicNumber[24]; (same magic)
> DWORD mReserved1; (0x20 0x74 0x67 0x74)
> WORD mBootMajorVersion;(0x30 0x00)
> WORD mBootMinorVersion;
> BYTE mMaxVersion; (QDL_MIN_VERSION = 0x06)
> BYTE mMinVersion; (QDL_MIN_VERSION = 0x06)
> DWORD mReserved2;
> DWORD mReserved3;
> BYTE mReserved4;
> WfORD mReserved5;
> WORD mReserved6;
> BYTE mFeatures; (QDL_FEATURE_GENERIC_UNFRAMED/0x10 |
> QDL_FEATURE_QDL_UNFRAMED/0x20 = 0x30)
> };
>
>
> > e) Then the Sierra Wireless downloader starts with a part of the
> > protocol I've found no docs for, but is implemented by the
> > gobi-loader. This is a start download (0x25) + ack (0x26),
> > followed
>
> See gobi-api/GobiAPI-1.0.40/Core/QDLEnum.h and gobi
> -api/GobiAPI_1.0.40/Core/QDLBuffers.cpp:
>
> 0x25 = eQDL_CMD_OPEN_UNFRAMED_REQ
> 0x26 = eQDL_CMD_OPEN_UNFRAMED_RSP
>
> > by data (0x27) and ack (0x28)
>
> 0x27 = eQDL_CMD_WRITE_UNFRAMED_REQ
> 0x28 = eQDL_CMD_WRITE_UNFRAMED_RSP
>
> > The most difficult part here, is probably getting the 0x25
> > request
> > right. This will tell the firware what kind of file we are
> > sending,
> > and the size it should expect to receive. If you look at the
> > gobi-loader, you'll see that it sends several files.
>
> gobi-api/GobiAPI_1.0.40/GobiQDLService/Main.cpp::Run() shows some of
> this.
>
> > The Sierra downloader sends a single complete image, typically
> > using a
> > request like this (from an upgrade of an MC7710 to 03.05.24):
> >
> > 0040 7e 25 80 1c 38 4f 02 01 8c 36 4f 02 00 00 01 01
> > ~%..8O...6O.....
> > 0050 02 00 00 00 01 90 00 08 cb 4a 46 55 4c 4c 00 00
> > .........JFULL..
> > 0060 00 00 00 00 00 00 00 00 00 00 00 00 00 00 01 01
> > ................
> > 0070 02 00 00 08 cc da 00 08 d1 72 46 55 4c 4c 00 00
> > .........rFULL..
> > 0080 00 00 00 00 00 00 00 00 00 00 00 00 00 00 01 02
> > ................
> > 0090 00 00 00 11 9e 4c 02 3d 99 d0 46 55 4c 4c 00 00
> > .....L.=..FULL..
> > 00a0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
> > ................
> > 00b0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
> > ................
> > 00c0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
> > ................
> > 00d0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
> > ................
> > 00e0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
> > ................
> > 00f0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
> > ................
> > 0100 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
> > ................
> > 0110 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
> > ................
> > 0120 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
> > ................
> > 0130 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
> > ................
> > 0140 00 00 00 00 00 00 00 00 00 00 00 00 00 00 d8 2f
> > .............../
> > 0150 cf 2b 00 00 00 03 ff ff ff ff 53 50 4b 47 39 32
> > .+........SPKG92
> > 0160 30 30 02 4f 36 8c 6d 11 b8 2a 39 39 39 39 39 39
> > 00.O6.m..*999999
> > 0170 39 5f 39 39 39 39 39 39 39 5f 39 32 30 30 5f 30
> > 9_9999999_9200_0
> > 0180 33 2e 30 35 2e 32 34 2e 30 30 5f 30 30 5f 67 65
> > 3.05.24.00_00_ge
> > 0190 6e 65 72 69 63 5f 30 30 30 2e 30 30 30 5f 30 30
> > neric_000.000_00
> > 01a0 31 5f 53 50 4b 47 5f 4d 43 00 00 00 00 00 00 00
> > 1_SPKG_MC.......
> > 01b0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 30 35
> > ..............05
> > 01c0 2f 30 32 2f 31 33 00 00 00 00 00 00 00 00 00 00
> > /02/13..........
> > 01d0 00 00 00 00 00 00 00 00 00 00 00 00 00 01 ae da
> > ................
> > 01e0 7e ~
> >
> >
> > There is lots of interesting info in the above, but this part
> > seems
> > important to understand the reply: 80 1c 38 4f 02 01 8c 36 4f 02
>
> struct sQDLRawOpenUnframedReq {
> BYTE mCommandCode; (0x25)
> BYTE mImageType; (0x80) (used as eQDL_IMAGE_*)
> DWORD mImageLength; (0x024f381c)
> BYTE mWindowSize; (0x01, yes really 1)
> DWORD mUnframedChunkSize; (0x024f368c)
> WORD mReserved1; (0x0000)
> };
>
> Oddly GobiAPI sets the chunk size to QDL_MAX_CHUNK_SIZE = 1024 * 1024
> *
> 64, so not sure where this one's coming from.
>
> > This looks like "byte, le32, byte, le32". The first "byte"
> > appears
> > to
> > tell what type of file this is (see gobi-loader). The second is
> > always(?) 1. And the two "le32" numbers look like image sizes.
> > This
> > is
> > also confirmed by gobi-loader. Match 0x024f368c (38745740) with
> > this:
>
> > $ ls -l
> > /tmp/9999999_9999999_9200_03.05.24.00_00_generic_000.000_001_SPKG_M
> > C.
> > cwe
> > -rw-r--r-- 1 bjorn bjorn 38746140 May 30 2013
> > /tmp/9999999_9999999_9200_03.05.24.00_00_generic_000.000_001_SPKG_M
> > C.
> > cwe
> >
> > And notice the same sequence in the reply ack, preceded by an
> > unknown
> > 16bit zero parameter:
> >
> > 0040 7e 26 00 00 01 8c 36 4f 02 e7 2f 7e
> > ~&....6O../~
>
> Your unknown is mStatus.
>
> struct sQDLRawOpenUnframedRsp {
> BYTE mCommandCode;
> WORD mStatus;
> BYTE mWindowSize;
> DWORD mUnframedChunkSize;
> };
>
> >
> > There are two notable differences in the above 0x25 request
> > compared
> > to the ones generated by gobi-loader
> > 1) the above is much longer
> > 2) the above has slightly different "size" numbers
> >
> > The difference is 0x024f381c - 0x024f368c = 0x190 (400d), which
> > is
> > exactly the number of "extra" data bytes in the 0x25 request.
> > Those
> > 400 bytes is the beginning of the firmware image:
>
> Odd; GobiAPI doesn't show any firmware data being attached to the
> eQDL_CMD_OPEN_UNFRAMED_REQ, it sends the REQ, parses the RSP, then
> starts sending data with eQDL_CMD_WRITE_UNFRAMED_REQ. I wonder if
> this
> is Sierra-specific or it it's a Qualcomm enhancement since the
> GobiAPI
> drops stopped in 2013.
>
> > 00000000 01 01 02 00 00 00 01 90 00 08 cb 4a 46 55 4c 4c
> > |...........JFULL|
> > 00000010 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
> > |................|
> > 00000020 01 01 02 00 00 08 cc da 00 08 d1 72 46 55 4c 4c
> > |...........rFULL|
> > 00000030 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
> > |................|
> > 00000040 01 02 00 00 00 11 9e 4c 02 3d 99 d0 46 55 4c 4c
> > |.......L.=..FULL|
> > 00000050 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
> > |................|
> > 00000060 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
> > |................|
> > 00000070 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
> > |................|
> > 00000080 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
> > |................|
> > 00000090 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
> > |................|
> > 000000a0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
> > |................|
> > 000000b0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
> > |................|
> > 000000c0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
> > |................|
> > 000000d0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
> > |................|
> > 000000e0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
> > |................|
> > 000000f0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
> > |................|
> > 00000100 d8 2f cf 2b 00 00 00 03 ff ff ff ff 53 50 4b 47
> > |./.+........SPKG|
> > 00000110 39 32 30 30 02 4f 36 8c 6d 11 b8 2a 39 39 39 39
> > |9200.O6.m..*9999|
> > 00000120 39 39 39 5f 39 39 39 39 39 39 39 5f 39 32 30 30
> > |999_9999999_9200|
> > 00000130 5f 30 33 2e 30 35 2e 32 34 2e 30 30 5f 30 30 5f
> > |_03.05.24.00_00_|
> > 00000140 67 65 6e 65 72 69 63 5f 30 30 30 2e 30 30 30 5f
> > |generic_000.000_|
> > 00000150 30 30 31 5f 53 50 4b 47 5f 4d 43 00 00 00 00 00
> > |001_SPKG_MC.....|
> > 00000160 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
> > |................|
> > 00000170 30 35 2f 30 32 2f 31 33 00 00 00 00 00 00 00 00
> > |05/02/13........|
> > 00000180 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 01
> > |................|
> >
> >
> >
> >
> > f) so far we've seen HDLC framing. The 0x27 data frames following
> > the
> > above is sent without framing. They have a 13-byte header,
> > followed
> > by the next x bytes of the image. In my case, each of these were
> > split in four 0x800 byte URBs and one URB of 1661 bytes (all
> > starting
> > at 0040 here due to the URB header, which I have removed):
> >
> >
> > 0040 27 00 00 00 00 00 00 70 1e 00 00 73 82 00 00 00
> > '......p...s....
> > 0050 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
> > ................
> > 0060 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
> > ................
> > ..
> > 0820 ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff
> > ................
> > 0830 ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff
> > ................
> >
> > 0040 ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff
> > ................
> > 0050 ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff
> > ................
> > ..
> > 0820 ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff
> > ................
> > 0830 ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff
> > ................
> >
> > 0040 ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff
> > ................
> > 0050 ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff
> > ................
> > ..
> > 0820 ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff
> > ................
> > 0830 ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff
> > ................
> >
> > 0040 ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff
> > ................
> > 0050 ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff
> > ................
> > 0060 ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff
> > ................
> > ..
> > 0690 ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff
> > ................
> > 06a0 ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff
> > ................
> > 06b0 ff ff ff ff ff ff ff ff ff ff ff ff ff
> > .............
> >
> >
> > So what we see is a total of 13 header bytes and 3*2048+1648=7792
> > data
> > bytes. The header is a sequence number (le16 or le32?), followed
> > by
> > an unknown 16 or 32 bit value (always? 0), the size of the data
> > packet
> > (0x00001e70=7792d) and a checksum. I don't know if the checksum
> > is
> > calculated over all the 7805 bytes, but I assume it is.
> >
> >
> > This is followed by reply starting with the same sequence number:
> >
> > 0040 7e 28 00 00 00 00 00 00 00 00 14 39 7e
> > ~(.........9~
> >
> > Then this is repeated again and again with exactly 0x2000 bytes
> > transfers (notice the sequence number being 0x00000001 here):
> >
> > 0040 27 01 00 00 00 00 00 00 20 00 00 a4 62 ff ff ff '.......
> > ...b...
> > 0050 ff ff ff ff ff ff ff ff ff ff ff ff ff d1 dc 4b
> > ...............K
> > 0060 84 34 10 d7 73 5a 43 0b 7d ff ff ff ff ff ff ff
> > .4..sZC.}.......
> > 0070 ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff ff
> > ................
> >
> >
> > Until the last transfer which also is slightly shorter to match
> > the
> > total:
> >
> > 0040 27 79 12 00 00 00 00 1c 18 00 00 86 54 78 a8 00
> > 'y..........Tx..
> >
> > 0040 7e 28 79 12 00 00 00 00 00 00 1c 9f 7e
> > ~(y.........~
> >
> >
> > So in total, we transferred
> >
> > 400 bytes in the 0x25 request
> > + 0x1e70 bytes in the first 0x27 request
> > + 0x1278 times 0x2000 bytes full sized 0x27 requests
> > + 0x181c bytes in the last 0x27 request
> > = 38746140 bytes
> >
> > Matching the image file size. Good. What we don't know is why
> > the
> > first transfer is slightly shorter, or why we have the first 400
> > bytes transferred as part of the 0x25 request.
> >
> >
> > g) The procedure is terminated with a 0x29 request and 0x2a ack:
> >
> > 0040 7e 29 bb 4c 7e ~).L~
> > 0040 7e 2a 00 00 00 00 4e e3 7e ~*....N.~
>
> eQDL_CMD_SESSION_DONE_REQ and eQDL_CMD_SESSION_DONE_RSP
>
> >
> > h) Then we send a 0x2d request, which is not part of the
> > gobi-loader. This request causes an immediate reboot into
> > application
> > mode:
> >
> > 0040 7e 2d 9f 0a 7e ~-..~
>
> eQDL_CMD_SESSION_CLOSE_REQ
>
> Dan
>
> > The first reboot will take some time, and I believe it also could
> > be
> > followed by more reboots before the process is complete. Then,
> > if
> > you
> > are lucky, the modem will boot a new firmware version in QMI
> > mode.
> >
> > If not, then you are most likely screwed and your modem is now an
> > expensive dummy slot filler.
> >
> >
> >
> > Bjørn
> >
> >
> >
> >
> > [1] assumed vendor specific version info request. typical result:
> >
> > QMI frame #0
> > > > > > > > QMUX:
> > > > > > > > length = 103
> > > > > > > > flags = 0x80
> > > > > > > > service = "dms"
> > > > > > > > client = 2
> > > > > > > > QMI:
> > > > > > > > flags = "response"
> > > > > > > > transaction = 5
> > > > > > > > tlv_length = 91
> > > > > > > > message = (0x5556)
> > > > > > > > TLV:
> > > > > > > > type = 0x02
> > > > > > > > length = 4
> > > > > > > > value = 00:00:00:00
> > > > > > > > TLV:
> > > > > > > > type = 0x16
> > > > > > > > length = 7
> > > > > > > > value = 30:30:30:2E:30:30:35
> > > > > > > > TLV:
> > > > > > > > type = 0x15
> > > > > > > > length = 2
> > > > > > > > value = 31:00
> > > > > > > > TLV:
> > > > > > > > type = 0x13
> > > > > > > > length = 8
> > > > > > > > value = 31:31:30:32:34:37:36:00
> > > > > > > > TLV:
> > > > > > > > type = 0x12
> > > > > > > > length = 21
> > > > > > > > value =
> > > > > > > > 53:57:49:39:58:33:30:43:5F:30:31:2E:30:38:2E:30:37:2E:3
> > > > > > > > 0:
> > > > > > > > 30:00
> > > > > > > > TLV:
> > > > > > > > type = 0x11
> > > > > > > > length = 21
> > > > > > > > value =
> > > > > > > > 53:57:49:39:58:33:30:43:5F:30:31:2E:30:38:2E:30:37:2E:3
> > > > > > > > 0:
> > > > > > > > 30:00
> > > > > > > > TLV:
> > > > > > > > type = 0x10
> > > > > > > > length = 7
> > > > > > > > value = 4D:43:37:34:35:35:00
> >
> > (note that all these except 0x16 are 0x00 terminated)
> >
> > 0x10 => MC7455
> > 0x11 => SWI9X30C_01.08.07.00
> > 0x12 => SWI9X30C_01.08.07.00
> > 0x13 => 1102476
> > 0x15 => 1
> > 0x16 => 000.005
> >
> > [2] https://github.com/ghassani/openpst/blob/master/src/qc/dload.h
> >
> > [3]
> > https://github.com/ghassani/openpst/blob/master/src/qc/streaming_
> > dload.h
> >
> > [4] http://www.codon.org.uk/~mjg59/gobi_loader/
> > _______________________________________________
> > libqmi-devel mailing list
> > libqmi-devel at lists.freedesktop.org
> > http://lists.freedesktop.org/mailman/listinfo/libqmi-devel
> _______________________________________________
> libqmi-devel mailing list
> libqmi-devel at lists.freedesktop.org
> http://lists.freedesktop.org/mailman/listinfo/libqmi-devel
More information about the libqmi-devel
mailing list