~clint-fewbar/ubuntu/precise/erlang/merge-15b

« back to all changes in this revision

Viewing changes to lib/xmerl/test/xmerl_appup_test.erl

  • Committer: Package Import Robot
  • Author(s): Sergei Golovan
  • Date: 2011-12-15 19:20:10 UTC
  • mfrom: (1.1.18) (3.5.15 sid)
  • mto: (3.5.16 sid)
  • mto: This revision was merged to the branch mainline in revision 33.
  • Revision ID: package-import@ubuntu.com-20111215192010-jnxcfe3tbrpp0big
Tags: 1:15.b-dfsg-1
* New upstream release.
* Upload to experimental because this release breaks external drivers
  API along with ABI, so several applications are to be fixed.
* Removed SSL patch because the old SSL implementation is removed from
  the upstream distribution.
* Removed never used patch which added native code to erlang beam files.
* Removed the erlang-docbuilder binary package because the docbuilder
  application was dropped by upstream.
* Documented dropping ${erlang-docbuilder:Depends} substvar in
  erlang-depends(1) manpage.
* Made erlang-base and erlang-base-hipe provide virtual package
  erlang-abi-15.b (the number means the first erlang version, which
  provides current ABI).

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
%%
 
2
%% %CopyrightBegin%
 
3
%%
 
4
%% Copyright Ericsson AB 2004-2011. All Rights Reserved.
 
5
%%
 
6
%% The contents of this file are subject to the Erlang Public License,
 
7
%% Version 1.1, (the "License"); you may not use this file except in
 
8
%% compliance with the License. You should have received a copy of the
 
9
%% Erlang Public License along with this software. If not, it can be
 
10
%% retrieved online at http://www.erlang.org/.
 
11
%%
 
12
%% Software distributed under the License is distributed on an "AS IS"
 
13
%% basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See
 
14
%% the License for the specific language governing rights and limitations
 
15
%% under the License.
 
16
%%
 
17
%% %CopyrightEnd%
 
18
%%
 
19
%%
 
20
%%----------------------------------------------------------------------
 
21
%% Purpose: Verify the application specifics of the Megaco application
 
22
%%----------------------------------------------------------------------
 
23
-module(xmerl_appup_test).
 
24
 
 
25
-compile(export_all).
 
26
 
 
27
%-include("megaco_test_lib.hrl").
 
28
 
 
29
 
 
30
%t()     -> megaco_test_lib:t(?MODULE).
 
31
%t(Case) -> megaco_test_lib:t({?MODULE, Case}).
 
32
 
 
33
 
 
34
%% Test server callbacks
 
35
% init_per_testcase(Case, Config) ->
 
36
%     megaco_test_lib:init_per_testcase(Case, Config).
 
37
 
 
38
% end_per_testcase(Case, Config) ->
 
39
%     megaco_test_lib:end_per_testcase(Case, Config).
 
40
 
 
41
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
 
42
 
 
43
all() -> 
 
44
    [appup].
 
45
 
 
46
groups() -> 
 
47
    [].
 
48
 
 
49
init_per_group(_GroupName, Config) ->
 
50
    Config.
 
51
 
 
52
end_per_group(_GroupName, Config) ->
 
53
    Config.
 
54
 
 
55
 
 
56
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
 
57
 
 
58
init_per_suite(suite) -> [];
 
59
init_per_suite(doc) -> [];
 
60
init_per_suite(Config) when is_list(Config) ->
 
61
    AppFile   = file_name(xmerl, ".app"),
 
62
    AppupFile = file_name(xmerl, ".appup"),
 
63
    [{app_file, AppFile}, {appup_file, AppupFile}|Config].
 
64
    
 
65
 
 
66
file_name(App, Ext) ->
 
67
    LibDir = code:lib_dir(App),
 
68
    filename:join([LibDir, "ebin", atom_to_list(App) ++ Ext]).
 
69
 
 
70
 
 
71
end_per_suite(suite) -> [];
 
72
end_per_suite(doc) -> [];
 
73
end_per_suite(Config) when is_list(Config) ->
 
74
    Config.
 
75
 
 
76
 
 
77
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
 
78
 
 
79
appup(suite) ->
 
80
    [];
 
81
appup(doc) ->
 
82
    "perform a simple check of the appup file";
 
83
appup(Config) when is_list(Config) ->
 
84
    AppupFile = key1search(appup_file, Config),
 
85
    AppFile   = key1search(app_file, Config),
 
86
    Modules   = modules(AppFile),
 
87
    check_appup(AppupFile, Modules).
 
88
 
 
89
modules(File) ->
 
90
    case file:consult(File) of
 
91
        {ok, [{application,xmerl,Info}]} ->
 
92
            case lists:keysearch(modules,1,Info) of
 
93
                {value, {modules, Modules}} ->
 
94
                    Modules;
 
95
                false ->
 
96
                    fail({bad_appinfo, Info})
 
97
            end;
 
98
        Error ->
 
99
            fail({bad_appfile, Error})
 
100
    end.
 
101
 
 
102
    
 
103
check_appup(AppupFile, Modules) ->
 
104
    case file:consult(AppupFile) of
 
105
        {ok, [{V, UpFrom, DownTo}]} ->
 
106
            io:format("V= ~p, UpFrom= ~p, DownTo= ~p, Modules= ~p~n",
 
107
                      [V, UpFrom, DownTo, Modules]),
 
108
            check_appup(V, UpFrom, DownTo, Modules);
 
109
        Else ->
 
110
            fail({bad_appupfile, Else})
 
111
    end.
 
112
 
 
113
 
 
114
check_appup(V, UpFrom, DownTo, Modules) ->
 
115
    check_version(V),
 
116
    check_depends(up,   UpFrom, Modules),
 
117
    check_depends(down, DownTo, Modules),
 
118
    ok.
 
119
 
 
120
 
 
121
check_depends(_, [], _) ->
 
122
    ok;
 
123
check_depends(UpDown, [Dep|Deps], Modules) ->
 
124
    check_depend(UpDown, Dep, Modules),
 
125
    check_depends(UpDown, Deps, Modules).
 
126
 
 
127
 
 
128
check_depend(up,I={add_application, _App}, Modules) ->
 
129
    d("check_instructions(~w) -> entry with"
 
130
      "~n   Instruction:       ~p"
 
131
      "~n   Modules: ~p", [up,I , Modules]),
 
132
    ok;
 
133
check_depend(down,I={remove_application, _App}, Modules) ->
 
134
    d("check_instructions(~w) -> entry with"
 
135
      "~n   Instruction:       ~p"
 
136
      "~n   Modules: ~p", [down,I , Modules]),
 
137
    ok;
 
138
check_depend(UpDown, {V, Instructions}, Modules) ->
 
139
    d("check_instructions(~w) -> entry with"
 
140
      "~n   V:       ~p"
 
141
      "~n   Modules: ~p", [UpDown, V, Modules]),
 
142
    check_version(V),
 
143
    case check_instructions(UpDown, 
 
144
                            Instructions, Instructions, [], [], Modules) of
 
145
        {_Good, []} ->
 
146
            ok;
 
147
        {_, Bad} ->
 
148
            fail({bad_instructions, Bad, UpDown})
 
149
    end.
 
150
 
 
151
 
 
152
check_instructions(_, [], _, Good, Bad, _) ->
 
153
    {lists:reverse(Good), lists:reverse(Bad)};
 
154
check_instructions(UpDown, [Instr|Instrs], AllInstr, Good, Bad, Modules) ->
 
155
    d("check_instructions(~w) -> entry with"
 
156
      "~n   Instr: ~p", [UpDown,Instr]),
 
157
    case (catch check_instruction(UpDown, Instr, AllInstr, Modules)) of
 
158
        ok ->
 
159
            check_instructions(UpDown, Instrs, AllInstr, 
 
160
                               [Instr|Good], Bad, Modules);
 
161
        {error, Reason} ->
 
162
            d("check_instructions(~w) -> bad instruction: "
 
163
              "~n   Reason: ~p", [UpDown,Reason]),
 
164
            check_instructions(UpDown, Instrs, AllInstr, Good, 
 
165
                               [{Instr, Reason}|Bad], Modules)
 
166
    end.
 
167
 
 
168
%% A new module is added
 
169
check_instruction(up, {add_module, Module}, _, Modules) 
 
170
  when is_atom(Module) ->
 
171
    d("check_instruction -> entry when up-add_module instruction with"
 
172
      "~n   Module: ~p", [Module]),
 
173
    check_module(Module, Modules);
 
174
 
 
175
%% An old module is re-added
 
176
check_instruction(down, {add_module, Module}, _, Modules) 
 
177
  when is_atom(Module) ->
 
178
    d("check_instruction -> entry when down-add_module instruction with"
 
179
      "~n   Module: ~p", [Module]),
 
180
    case (catch check_module(Module, Modules)) of
 
181
        {error, {unknown_module, Module, Modules}} ->
 
182
            ok;
 
183
        ok ->
 
184
            local_error({existing_readded_module, Module})
 
185
    end;
 
186
 
 
187
%% Removing a module on upgrade: 
 
188
%% - the module has been removed from the app-file.
 
189
%% - check that no module depends on this (removed) module
 
190
check_instruction(up, {remove, {Module, Pre, Post}}, _, Modules) 
 
191
  when is_atom(Module), is_atom(Pre), is_atom(Post) ->
 
192
    d("check_instruction -> entry when up-remove instruction with"
 
193
      "~n   Module: ~p"
 
194
      "~n   Pre:    ~p"
 
195
      "~n   Post:   ~p", [Module, Pre, Post]),
 
196
    case (catch check_module(Module, Modules)) of
 
197
        {error, {unknown_module, Module, Modules}} ->
 
198
            check_purge(Pre),
 
199
            check_purge(Post);
 
200
        ok ->
 
201
            local_error({existing_removed_module, Module})
 
202
    end;
 
203
 
 
204
%% Removing a module on downgrade: the module exist
 
205
%% in the app-file.
 
206
check_instruction(down, {remove, {Module, Pre, Post}}, AllInstr, Modules) 
 
207
  when is_atom(Module), is_atom(Pre), is_atom(Post) ->
 
208
    d("check_instruction -> entry when down-remove instruction with"
 
209
      "~n   Module: ~p"
 
210
      "~n   Pre:    ~p"
 
211
      "~n   Post:   ~p", [Module, Pre, Post]),
 
212
    case (catch check_module(Module, Modules)) of
 
213
        ok ->
 
214
            check_purge(Pre),
 
215
            check_purge(Post),
 
216
            check_no_remove_depends(Module, AllInstr);
 
217
        {error, {unknown_module, Module, Modules}} ->
 
218
            local_error({nonexisting_removed_module, Module})
 
219
    end;
 
220
 
 
221
check_instruction(_, {load_module, Module, Pre, Post, Depend}, 
 
222
                  AllInstr, Modules) 
 
223
  when is_atom(Module), is_atom(Pre), is_atom(Post), is_list(Depend) ->
 
224
    d("check_instruction -> entry when load_module instruction with"
 
225
      "~n   Module: ~p"
 
226
      "~n   Pre:    ~p"
 
227
      "~n   Post:   ~p"
 
228
      "~n   Depend: ~p", [Module, Pre, Post, Depend]),
 
229
    check_module(Module, Modules),
 
230
    check_module_depend(Module, Depend, Modules),
 
231
    check_module_depend(Module, Depend, updated_modules(AllInstr, [])),
 
232
    check_purge(Pre),
 
233
    check_purge(Post);
 
234
 
 
235
check_instruction(_, {update, Module, Change, Pre, Post, Depend}, 
 
236
                  AllInstr, Modules) 
 
237
  when is_atom(Module), is_atom(Pre), is_atom(Post), is_list(Depend) ->
 
238
    d("check_instruction -> entry when update instruction with"
 
239
      "~n   Module: ~p"
 
240
      "~n   Change: ~p"
 
241
      "~n   Pre:    ~p"
 
242
      "~n   Post:   ~p"
 
243
      "~n   Depend: ~p", [Module, Change, Pre, Post, Depend]),
 
244
    check_module(Module, Modules),
 
245
    check_module_depend(Module, Depend, Modules),
 
246
    check_module_depend(Module, Depend, updated_modules(AllInstr, [])),
 
247
    check_change(Change),
 
248
    check_purge(Pre),
 
249
    check_purge(Post);
 
250
 
 
251
check_instruction(_, Instr, _AllInstr, _Modules) ->
 
252
    d("check_instruction -> entry when unknown instruction with"
 
253
      "~n   Instr: ~p", [Instr]),
 
254
    local_error({error, {unknown_instruction, Instr}}).
 
255
 
 
256
 
 
257
%% If Module X depends on Module Y, then module Y must have an update
 
258
%% instruction of some sort (otherwise the depend is faulty).
 
259
updated_modules([], Modules) ->
 
260
    d("update_modules -> entry when done with"
 
261
      "~n   Modules: ~p", [Modules]),
 
262
    Modules;
 
263
updated_modules([Instr |Instrs], Modules) ->
 
264
    d("update_modules -> entry with"
 
265
      "~n   Instr:   ~p"
 
266
      "~n   Modules: ~p", [Instr,Modules]),
 
267
    Module = instruction_module(Instr),
 
268
    d("update_modules -> Module: ~p", [Module]),
 
269
    updated_modules(Instrs, [Module|Modules]).
 
270
    
 
271
instruction_module({add_module, Module}) ->
 
272
    Module;
 
273
instruction_module({remove, {Module, _, _}}) ->
 
274
    Module;
 
275
instruction_module({load_module, Module, _, _, _}) ->
 
276
    Module;
 
277
instruction_module({update, Module, _, _, _, _}) ->
 
278
    Module;
 
279
instruction_module(Instr) ->
 
280
    d("instruction_module -> entry when unknown instruction with"
 
281
      "~n   Instr: ~p", [Instr]),
 
282
    local_error({error, {unknown_instruction, Instr}}).
 
283
    
 
284
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
 
285
 
 
286
check_version(V) when is_list(V) ->
 
287
    ok;
 
288
check_version(V) ->
 
289
    local_error({bad_version, V}).
 
290
 
 
291
 
 
292
check_module(M, Modules) when is_atom(M) ->
 
293
    case lists:member(M,Modules) of
 
294
        true ->
 
295
            ok;
 
296
        false ->
 
297
            local_error({unknown_module, M, Modules})
 
298
    end;
 
299
check_module(M, _) ->
 
300
    local_error({bad_module, M}).
 
301
 
 
302
 
 
303
check_module_depend(M, [], _) when is_atom(M) ->
 
304
    d("check_module_depend -> entry with"
 
305
      "~n   M: ~p", [M]),    
 
306
    ok;
 
307
check_module_depend(M, Deps, Modules) when is_atom(M), is_list(Deps) ->
 
308
    d("check_module_depend -> entry with"
 
309
      "~n   M: ~p"
 
310
      "~n   Deps: ~p"
 
311
      "~n   Modules: ~p", [M, Deps, Modules]),    
 
312
    case [Dep || Dep <- Deps, lists:member(Dep, Modules) == false] of
 
313
        [] ->
 
314
            ok;
 
315
        Unknown ->
 
316
            local_error({unknown_depend_modules, Unknown})
 
317
    end;
 
318
check_module_depend(_M, D, _Modules) ->
 
319
    d("check_module_depend -> entry when bad depend with"
 
320
      "~n   D: ~p", [D]),    
 
321
    local_error({bad_depend, D}).
 
322
 
 
323
 
 
324
check_no_remove_depends(_Module, []) ->
 
325
    ok;
 
326
check_no_remove_depends(Module, [Instr|Instrs]) ->
 
327
    check_no_remove_depend(Module, Instr),
 
328
    check_no_remove_depends(Module, Instrs).
 
329
 
 
330
check_no_remove_depend(Module, {load_module, Mod, _Pre, _Post, Depend}) ->
 
331
    case lists:member(Module, Depend) of
 
332
        true ->
 
333
            local_error({removed_module_in_depend, load_module, Mod, Module});
 
334
        false ->
 
335
            ok
 
336
    end;
 
337
check_no_remove_depend(Module, {update, Mod, _Change, _Pre, _Post, Depend}) ->
 
338
    case lists:member(Module, Depend) of
 
339
        true ->
 
340
            local_error({removed_module_in_depend, update, Mod, Module});
 
341
        false ->
 
342
            ok
 
343
    end;
 
344
check_no_remove_depend(_, _) ->
 
345
    ok.
 
346
    
 
347
 
 
348
check_change(soft) ->
 
349
    ok;
 
350
check_change({advanced, _Something}) ->
 
351
    ok;
 
352
check_change(Change) ->
 
353
    local_error({bad_change, Change}).
 
354
 
 
355
 
 
356
check_purge(soft_purge) ->
 
357
    ok;
 
358
check_purge(brutal_purge) ->
 
359
    ok;
 
360
check_purge(Purge) ->
 
361
    local_error({bad_purge, Purge}).
 
362
 
 
363
 
 
364
 
 
365
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
 
366
 
 
367
local_error(Reason) ->
 
368
    throw({error, Reason}).
 
369
 
 
370
fail(Reason) ->
 
371
    exit({suite_failed, Reason}).
 
372
 
 
373
key1search(Key, L) ->
 
374
    case lists:keysearch(Key, 1, L) of
 
375
        undefined ->
 
376
            fail({not_found, Key, L});
 
377
        {value, {Key, Value}} ->
 
378
            Value
 
379
    end.
 
380
 
 
381
 
 
382
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
 
383
 
 
384
d(F, A) ->
 
385
    d(false, F, A).
 
386
 
 
387
d(true, F, A) ->
 
388
    io:format(F ++ "~n", A);
 
389
d(_, _, _) ->
 
390
    ok.
 
391
 
 
392