File: v21-gm-md5.sql

package info (click to toggle)
gnumed-server 22.31-1
  • links: PTS, VCS
  • area: main
  • in suites: forky, sid, trixie
  • size: 46,268 kB
  • sloc: sql: 1,217,633; python: 15,878; sh: 1,590; makefile: 20
file content (57 lines) | stat: -rw-r--r-- 1,809 bytes parent folder | download | duplicates (5)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
-- ==============================================================
-- GNUmed database schema change script
--
-- License: GPL v2 or later
-- Author: karsten.hilbert@gmx.net
--
-- ==============================================================
\set ON_ERROR_STOP 1
--set default_transaction_read_only to off;

-- --------------------------------------------------------------
create or replace function gm.lo_chunked_md5(oid, int)
	returns text
	language 'plpgsql'
	stable strict
	as '
DECLARE
	lo_id alias for $1;
	chunk_size alias for $2;
	_lo_fd integer;
	_lo_size integer;
	_chunk_count integer;
	_remainder integer;
	_md5_concat text;
	INV_READ constant integer := x''40000''::integer;
	SEEK_SET constant integer := 0;
	SEEK_END constant integer := 2;
BEGIN
	-- check for existence of lo_id ?

	_lo_fd := lo_open(lo_id, INV_READ);
	-- get size
	_lo_size := lo_lseek(_lo_fd, 0, SEEK_END);
	PERFORM lo_close(_lo_fd);						-- move further down if loread() proves faster

	-- calculate chunks and remainder
	_chunk_count := _lo_size / chunk_size;
	_remainder := _lo_size % chunk_size;

	-- loop over chunks
	_md5_concat := '''';
	FOR _chunk_id in 1.._chunk_count LOOP
		_md5_concat := _md5_concat || md5(lo_get(lo_id, (_chunk_id - 1) * chunk_size, chunk_size));
		-- using loread() may be faster (as it directly accesses the
		-- existing lo_fd and thusly does not need to re-open the LO
		-- each round)
	END LOOP;
	-- add remainder
	_md5_concat := _md5_concat || md5(lo_get(lo_id, _chunk_count * chunk_size, _remainder));

	return md5(_md5_concat);
END;';

comment on function gm.lo_chunked_md5(oid, int) is 'Function to create a chunked md5 sum on arbitrarily large LARGE OBJECTs.';

-- --------------------------------------------------------------
select gm.log_script_insertion('v21-gm-md5.sql', '21.0');