function  [R,S,iter] = enrichment(S0,F,G,TOL,IndBcnode,num_iter)
% function  [R,S,iter] = enrichment(S0,F,G,TOL,IndBcnode,num_iter)
% Computes a new sumand by fixed-point algorithm using PGD
% Universidad de Zaragoza - 2015
global vx vp
global num_iter_prev
global r1 r2 r3 r4 r5 s1 s2 s3

R = zeros(size(F,1),1); R0 = R; % Initial value R to compare in first loop.
h = size(vx,2); % Number functions of the source.
ExitFlag = 1;
iter = 0;
mxit = 100; % # of possible iterations for the fixed point algorithm.
Free = setdiff(1:numel(F(:,1)),IndBcnode);
%
% FIXED POINT ALGORITHM
%
while ExitFlag > TOL 
    %
    % LOOKING FOR R, KNOWNING S
    %
    matrixR = r1*(S0'*s1*S0); % T2K
    sourceR = zeros(size(F,1),1);
    for k1=1:h
        sourceR = sourceR + vx(:,k1)*(S0'*vp(:,k1)); % source term.
    end
    for i1=1:num_iter-1
        sourceR = sourceR - (r1*F(:,i1))*(S0'*s1*G(:,i1)); % T2F
    end    
    for i1=1:num_iter_prev
        matrixR = matrixR + ...
            r2{i1}.*(S0'*s2{i1}*S0) + ...
            r2{i1}'.*(S0'*s2{i1}*S0) + ...
            r3{i1}.*(S0'*s2{i1}*S0); % T4K, T6K, T9K
        for j1=1:num_iter-1
             sourceR = sourceR - ...
                 r2{i1}*F(:,j1)*(S0'*s2{i1}*G(:,j1)) - ...
                 r2{i1}'*F(:,j1)*(S0'*s2{i1}*G(:,j1)) - ...
                 r3{i1}*F(:,j1)*(S0'*s2{i1}*G(:,j1)); % T4F, T6F, T9F
        end
    end
    for i1=1:num_iter_prev*num_iter_prev
        matrixR = matrixR + ...
            r4{i1}.*(S0'*s3{i1}*S0) + ...
            0.5*r5{i1}.*(S0'*s3{i1}*S0); % T8K, T10K
        for j1=1:num_iter-1
            sourceR = sourceR - ...
                r4{i1}*F(:,j1).*(S0'*s3{i1}*G(:,j1)) - ...
                0.5*r5{i1}*F(:,j1).*(S0'*s3{i1}*G(:,j1)); % T8F, T10F
        end
    end
    %
    % SOLVE R
    %
    R(Free) = matrixR(Free,Free)\sourceR(Free);
    %
    % LOOKING FOR S, KNOWNING R
    %
    matrixS = (R'*r1*R).*s1; % T2K
    sourceS = zeros(size(G,1),1);
    for k1=1:h
        sourceS = sourceS + (R'*vx(:,k1))*vp(:,k1); % source term.
    end
    for i1=1:num_iter-1
        sourceS = sourceS - (R'*r1*F(:,i1))*(s1*G(:,i1)); % T2F
    end    
    for i1=1:num_iter_prev
        matrixS = matrixS + ...
            (R'*r2{i1}*R).*s2{i1} + ...
            (R'*r2{i1}'*R).*s2{i1} + ...
            (R'*r3{i1}*R).*s2{i1}; % T4K, T6K, T9K
        for j1=1:num_iter-1
             sourceS = sourceS - ...
                 (R'*r2{i1}*F(:,j1))*s2{i1}*G(:,j1) - ...
                 (R'*r2{i1}'*F(:,j1))*s2{i1}*G(:,j1) - ...
                 (R'*r3{i1}*F(:,j1))*s2{i1}*G(:,j1); % T4F, T6F, T9F
        end
    end    
    for i1=1:num_iter_prev*num_iter_prev
        matrixS = matrixS + ...
            (R'*r4{i1}*R).*s3{i1} + ...
            0.5*(R'*r5{i1}*R).*s3{i1}; % T8K, T10K
        for j1=1:num_iter-1
            sourceS = sourceS - ...
                (R'*r4{i1}*F(:,j1)).*(s3{i1}*G(:,j1)) - ...
                0.5*(R'*r5{i1}*F(:,j1)).*(s3{i1}*G(:,j1)); % T8F, T10F
        end
    end
    %
    % SOLVE S
    %
    S = matrixS\sourceS;
    S = S./norm(S); % We normalize S. R takes care of alpha constant.
    %
    % COMPUTING STOP CRITERIA
    %
    error = max(abs(sum(R0-R)),abs(sum(S0-S)));
    R0 = R; S0 = S;
    iter = iter + 1;
    if iter>mxit || abs(error)<TOL, 
        return
    end
end

return