xref: /petsc/src/tao/util/tao_util.c (revision 8e3154b540202849446f3fa52050464855c228d0)
1a7e14dcfSSatish Balay #include "petsc-private/petscimpl.h"
2a7e14dcfSSatish Balay #include "tao.h" /*I "tao.h" I*/
3a7e14dcfSSatish Balay #include "tao_util.h" /*I "tao_util.h" I*/
4a7e14dcfSSatish Balay 
5a7e14dcfSSatish Balay #undef __FUNCT__
6a7e14dcfSSatish Balay #define __FUNCT__ "VecPow"
7a7e14dcfSSatish Balay /*@
8a7e14dcfSSatish Balay   VecPow - Replaces each component of a vector by x_i^p
9a7e14dcfSSatish Balay 
10a7e14dcfSSatish Balay   Logically Collective on v
11a7e14dcfSSatish Balay 
12a7e14dcfSSatish Balay   Input Parameter:
13a7e14dcfSSatish Balay + v - the vector
14a7e14dcfSSatish Balay - p - the exponent to use on each element
15a7e14dcfSSatish Balay 
16a7e14dcfSSatish Balay   Output Parameter:
17a7e14dcfSSatish Balay . v - the vector
18a7e14dcfSSatish Balay 
19a7e14dcfSSatish Balay   Level: intermediate
20a7e14dcfSSatish Balay 
21a7e14dcfSSatish Balay @*/
22a7e14dcfSSatish Balay PetscErrorCode VecPow(Vec v, PetscReal p)
23a7e14dcfSSatish Balay {
24a7e14dcfSSatish Balay   PetscErrorCode ierr;
25a7e14dcfSSatish Balay   PetscInt n,i;
26a7e14dcfSSatish Balay   PetscReal *v1;
27a7e14dcfSSatish Balay 
28a7e14dcfSSatish Balay   PetscFunctionBegin;
29a7e14dcfSSatish Balay   PetscValidHeaderSpecific(v, VEC_CLASSID, 1);
30a7e14dcfSSatish Balay 
31a7e14dcfSSatish Balay   ierr = VecGetArray(v, &v1); CHKERRQ(ierr);
32a7e14dcfSSatish Balay   ierr = VecGetLocalSize(v, &n); CHKERRQ(ierr);
33a7e14dcfSSatish Balay 
34a7e14dcfSSatish Balay   if (1.0 == p) {
35a7e14dcfSSatish Balay   }
36a7e14dcfSSatish Balay   else if (-1.0 == p) {
37a7e14dcfSSatish Balay     for (i = 0; i < n; ++i){
38a7e14dcfSSatish Balay       v1[i] = 1.0 / v1[i];
39a7e14dcfSSatish Balay     }
40a7e14dcfSSatish Balay   }
41a7e14dcfSSatish Balay   else if (0.0 == p) {
42a7e14dcfSSatish Balay     for (i = 0; i < n; ++i){
43a7e14dcfSSatish Balay       /*  Not-a-number left alone
44a7e14dcfSSatish Balay 	  Infinity set to one  */
45a7e14dcfSSatish Balay       if (v1[i] == v1[i]) {
46a7e14dcfSSatish Balay         v1[i] = 1.0;
47a7e14dcfSSatish Balay       }
48a7e14dcfSSatish Balay     }
49a7e14dcfSSatish Balay   }
50a7e14dcfSSatish Balay   else if (0.5 == p) {
51a7e14dcfSSatish Balay     for (i = 0; i < n; ++i) {
52a7e14dcfSSatish Balay       if (v1[i] >= 0) {
53a7e14dcfSSatish Balay         v1[i] = PetscSqrtScalar(v1[i]);
54a7e14dcfSSatish Balay       }
55a7e14dcfSSatish Balay       else {
56a7e14dcfSSatish Balay         v1[i] = TAO_INFINITY;
57a7e14dcfSSatish Balay       }
58a7e14dcfSSatish Balay     }
59a7e14dcfSSatish Balay   }
60a7e14dcfSSatish Balay   else if (-0.5 == p) {
61a7e14dcfSSatish Balay     for (i = 0; i < n; ++i) {
62a7e14dcfSSatish Balay       if (v1[i] >= 0) {
63a7e14dcfSSatish Balay         v1[i] = 1.0 / PetscSqrtScalar(v1[i]);
64a7e14dcfSSatish Balay       }
65a7e14dcfSSatish Balay       else {
66a7e14dcfSSatish Balay         v1[i] = TAO_INFINITY;
67a7e14dcfSSatish Balay       }
68a7e14dcfSSatish Balay     }
69a7e14dcfSSatish Balay   }
70a7e14dcfSSatish Balay   else if (2.0 == p) {
71a7e14dcfSSatish Balay     for (i = 0; i < n; ++i){
72a7e14dcfSSatish Balay       v1[i] *= v1[i];
73a7e14dcfSSatish Balay     }
74a7e14dcfSSatish Balay   }
75a7e14dcfSSatish Balay   else if (-2.0 == p) {
76a7e14dcfSSatish Balay     for (i = 0; i < n; ++i){
77a7e14dcfSSatish Balay       v1[i] = 1.0 / (v1[i] * v1[i]);
78a7e14dcfSSatish Balay     }
79a7e14dcfSSatish Balay   }
80a7e14dcfSSatish Balay   else {
81a7e14dcfSSatish Balay     for (i = 0; i < n; ++i) {
82a7e14dcfSSatish Balay       if (v1[i] >= 0) {
83a7e14dcfSSatish Balay         v1[i] = PetscPowScalar(v1[i], p);
84a7e14dcfSSatish Balay       }
85a7e14dcfSSatish Balay       else {
86a7e14dcfSSatish Balay         v1[i] = TAO_INFINITY;
87a7e14dcfSSatish Balay       }
88a7e14dcfSSatish Balay     }
89a7e14dcfSSatish Balay   }
90a7e14dcfSSatish Balay 
91a7e14dcfSSatish Balay   ierr = VecRestoreArray(v,&v1); CHKERRQ(ierr);
92a7e14dcfSSatish Balay   PetscFunctionReturn(0);
93a7e14dcfSSatish Balay }
94a7e14dcfSSatish Balay 
95a7e14dcfSSatish Balay #undef __FUNCT__
96a7e14dcfSSatish Balay #define __FUNCT__ "VecMedian"
97a7e14dcfSSatish Balay /*@
98a7e14dcfSSatish Balay   VecMedian - Computes the componentwise median of three vectors
99a7e14dcfSSatish Balay   and stores the result in this vector.  Used primarily for projecting
100a7e14dcfSSatish Balay   a vector within upper and lower bounds.
101a7e14dcfSSatish Balay 
102a7e14dcfSSatish Balay   Logically Collective
103a7e14dcfSSatish Balay 
104a7e14dcfSSatish Balay   Input Parameters:
105a7e14dcfSSatish Balay . Vec1, Vec2, Vec3 - The three vectors
106a7e14dcfSSatish Balay 
107a7e14dcfSSatish Balay   Output Parameter:
108a7e14dcfSSatish Balay . VMedian - The median vector
109a7e14dcfSSatish Balay 
110a7e14dcfSSatish Balay   Level: advanced
111a7e14dcfSSatish Balay @*/
112a7e14dcfSSatish Balay PetscErrorCode VecMedian(Vec Vec1, Vec Vec2, Vec Vec3, Vec VMedian)
113a7e14dcfSSatish Balay {
114a7e14dcfSSatish Balay   PetscErrorCode ierr;
115a7e14dcfSSatish Balay   PetscInt i,n,low1,low2,low3,low4,high1,high2,high3,high4;
116a7e14dcfSSatish Balay   PetscReal *v1,*v2,*v3,*vmed;
117a7e14dcfSSatish Balay 
118a7e14dcfSSatish Balay   PetscFunctionBegin;
119a7e14dcfSSatish Balay   PetscValidHeaderSpecific(Vec1,VEC_CLASSID,1);
120a7e14dcfSSatish Balay   PetscValidHeaderSpecific(Vec2,VEC_CLASSID,2);
121a7e14dcfSSatish Balay   PetscValidHeaderSpecific(Vec3,VEC_CLASSID,3);
122a7e14dcfSSatish Balay   PetscValidHeaderSpecific(VMedian,VEC_CLASSID,4);
123a7e14dcfSSatish Balay 
124a7e14dcfSSatish Balay   if (Vec1==Vec2 || Vec1==Vec3){
125a7e14dcfSSatish Balay     ierr=VecCopy(Vec1,VMedian); CHKERRQ(ierr);
126a7e14dcfSSatish Balay     PetscFunctionReturn(0);
127a7e14dcfSSatish Balay   }
128a7e14dcfSSatish Balay   if (Vec2==Vec3){
129a7e14dcfSSatish Balay     ierr=VecCopy(Vec2,VMedian); CHKERRQ(ierr);
130a7e14dcfSSatish Balay     PetscFunctionReturn(0);
131a7e14dcfSSatish Balay   }
132a7e14dcfSSatish Balay 
133a7e14dcfSSatish Balay   PetscValidType(Vec1,1);
134a7e14dcfSSatish Balay   PetscValidType(Vec2,2);
135a7e14dcfSSatish Balay   PetscValidType(VMedian,4);
136a7e14dcfSSatish Balay   PetscCheckSameType(Vec1,1,Vec2,2); PetscCheckSameType(Vec1,1,VMedian,4);
137a7e14dcfSSatish Balay   PetscCheckSameComm(Vec1,1,Vec2,2); PetscCheckSameComm(Vec1,1,VMedian,4);
138a7e14dcfSSatish Balay 
139a7e14dcfSSatish Balay   ierr = VecGetOwnershipRange(Vec1, &low1, &high1); CHKERRQ(ierr);
140a7e14dcfSSatish Balay   ierr = VecGetOwnershipRange(Vec2, &low2, &high2); CHKERRQ(ierr);
141a7e14dcfSSatish Balay   ierr = VecGetOwnershipRange(Vec3, &low3, &high3); CHKERRQ(ierr);
142a7e14dcfSSatish Balay   ierr = VecGetOwnershipRange(VMedian, &low4, &high4); CHKERRQ(ierr);
143a7e14dcfSSatish Balay   if ( low1!= low2 || low1!= low3 || low1!= low4 ||
144a7e14dcfSSatish Balay        high1!= high2 || high1!= high3 || high1!= high4)
145a7e14dcfSSatish Balay     SETERRQ(PETSC_COMM_SELF,1,"InCompatible vector local lengths");
146a7e14dcfSSatish Balay 
147a7e14dcfSSatish Balay   ierr = VecGetArray(Vec1,&v1); CHKERRQ(ierr);
148a7e14dcfSSatish Balay   ierr = VecGetArray(Vec2,&v2); CHKERRQ(ierr);
149a7e14dcfSSatish Balay   ierr = VecGetArray(Vec3,&v3); CHKERRQ(ierr);
150a7e14dcfSSatish Balay 
151a7e14dcfSSatish Balay   if ( VMedian != Vec1 && VMedian != Vec2 && VMedian != Vec3){
152a7e14dcfSSatish Balay     ierr = VecGetArray(VMedian,&vmed); CHKERRQ(ierr);
153a7e14dcfSSatish Balay   } else if ( VMedian==Vec1 ){
154a7e14dcfSSatish Balay     vmed=v1;
155a7e14dcfSSatish Balay   } else if ( VMedian==Vec2 ){
156a7e14dcfSSatish Balay     vmed=v2;
157a7e14dcfSSatish Balay   } else {
158a7e14dcfSSatish Balay     vmed=v3;
159a7e14dcfSSatish Balay   }
160a7e14dcfSSatish Balay 
161a7e14dcfSSatish Balay   ierr=VecGetLocalSize(Vec1,&n); CHKERRQ(ierr);
162a7e14dcfSSatish Balay 
163a7e14dcfSSatish Balay   for (i=0;i<n;i++){
164a7e14dcfSSatish Balay     vmed[i]=PetscMax(PetscMax(PetscMin(v1[i],v2[i]),PetscMin(v1[i],v3[i])),PetscMin(v2[i],v3[i]));
165a7e14dcfSSatish Balay   }
166a7e14dcfSSatish Balay 
167a7e14dcfSSatish Balay   ierr = VecRestoreArray(Vec1,&v1); CHKERRQ(ierr);
168a7e14dcfSSatish Balay   ierr = VecRestoreArray(Vec2,&v2); CHKERRQ(ierr);
169a7e14dcfSSatish Balay   ierr = VecRestoreArray(Vec3,&v2); CHKERRQ(ierr);
170a7e14dcfSSatish Balay 
171a7e14dcfSSatish Balay   if (VMedian!=Vec1 && VMedian != Vec2 && VMedian != Vec3){
172a7e14dcfSSatish Balay     ierr = VecRestoreArray(VMedian,&vmed); CHKERRQ(ierr);
173a7e14dcfSSatish Balay   }
174a7e14dcfSSatish Balay 
175a7e14dcfSSatish Balay   PetscFunctionReturn(0);
176a7e14dcfSSatish Balay }
177a7e14dcfSSatish Balay 
178a7e14dcfSSatish Balay PETSC_STATIC_INLINE PetscReal Fischer(PetscReal a, PetscReal b)
179a7e14dcfSSatish Balay {
180a7e14dcfSSatish Balay   /* Method suggested by Bob Vanderbei */
181a7e14dcfSSatish Balay    if (a + b <= 0) {
182a7e14dcfSSatish Balay      return PetscSqrtScalar(a*a + b*b) - (a + b);
183a7e14dcfSSatish Balay    }
184a7e14dcfSSatish Balay    return -2.0*a*b / (PetscSqrtScalar(a*a + b*b) + (a + b));
185a7e14dcfSSatish Balay }
186a7e14dcfSSatish Balay 
187a7e14dcfSSatish Balay #undef __FUNCT__
188a7e14dcfSSatish Balay #define __FUNCT__ "VecFischer"
189a7e14dcfSSatish Balay /*@
190a7e14dcfSSatish Balay    VecFischer - Evaluates the Fischer-Burmeister function for complementarity
191a7e14dcfSSatish Balay    problems.
192a7e14dcfSSatish Balay 
193a7e14dcfSSatish Balay    Logically Collective on vectors
194a7e14dcfSSatish Balay 
195a7e14dcfSSatish Balay    Input Parameters:
196a7e14dcfSSatish Balay +  X - current point
197a7e14dcfSSatish Balay .  F - function evaluated at x
198a7e14dcfSSatish Balay .  L - lower bounds
199a7e14dcfSSatish Balay -  U - upper bounds
200a7e14dcfSSatish Balay 
201a7e14dcfSSatish Balay    Output Parameters:
202a7e14dcfSSatish Balay .  FB - The Fischer-Burmeister function vector
203a7e14dcfSSatish Balay 
204a7e14dcfSSatish Balay    Notes:
205a7e14dcfSSatish Balay    The Fischer-Burmeister function is defined as
206a7e14dcfSSatish Balay $        phi(a,b) := sqrt(a*a + b*b) - a - b
207a7e14dcfSSatish Balay    and is used reformulate a complementarity problem as a semismooth
208a7e14dcfSSatish Balay    system of equations.
209a7e14dcfSSatish Balay 
210a7e14dcfSSatish Balay    The result of this function is done by cases:
211a7e14dcfSSatish Balay +  l[i] == -infinity, u[i] == infinity  -- fb[i] = -f[i]
212a7e14dcfSSatish Balay .  l[i] == -infinity, u[i] finite       -- fb[i] = phi(u[i]-x[i], -f[i])
213a7e14dcfSSatish Balay .  l[i] finite,       u[i] == infinity  -- fb[i] = phi(x[i]-l[i],  f[i])
214a7e14dcfSSatish Balay .  l[i] finite < u[i] finite -- fb[i] = phi(x[i]-l[i], phi(u[i]-x[i], -f[u]))
215a7e14dcfSSatish Balay -  otherwise l[i] == u[i] -- fb[i] = l[i] - x[i]
216a7e14dcfSSatish Balay 
217a7e14dcfSSatish Balay    Level: developer
218a7e14dcfSSatish Balay 
219a7e14dcfSSatish Balay @*/
220a7e14dcfSSatish Balay PetscErrorCode VecFischer(Vec X, Vec F, Vec L, Vec U, Vec FB)
221a7e14dcfSSatish Balay {
222a7e14dcfSSatish Balay   PetscReal *x, *f, *l, *u, *fb;
223a7e14dcfSSatish Balay   PetscReal xval, fval, lval, uval;
224a7e14dcfSSatish Balay   PetscErrorCode ierr;
225a7e14dcfSSatish Balay   PetscInt low[5], high[5], n, i;
226a7e14dcfSSatish Balay 
227a7e14dcfSSatish Balay   PetscFunctionBegin;
228a7e14dcfSSatish Balay   PetscValidHeaderSpecific(X, VEC_CLASSID,1);
229a7e14dcfSSatish Balay   PetscValidHeaderSpecific(F, VEC_CLASSID,2);
230a7e14dcfSSatish Balay   PetscValidHeaderSpecific(L, VEC_CLASSID,3);
231a7e14dcfSSatish Balay   PetscValidHeaderSpecific(U, VEC_CLASSID,4);
232a7e14dcfSSatish Balay   PetscValidHeaderSpecific(FB, VEC_CLASSID,4);
233a7e14dcfSSatish Balay 
234a7e14dcfSSatish Balay   ierr = VecGetOwnershipRange(X, low, high); CHKERRQ(ierr);
235a7e14dcfSSatish Balay   ierr = VecGetOwnershipRange(F, low + 1, high + 1); CHKERRQ(ierr);
236a7e14dcfSSatish Balay   ierr = VecGetOwnershipRange(L, low + 2, high + 2); CHKERRQ(ierr);
237a7e14dcfSSatish Balay   ierr = VecGetOwnershipRange(U, low + 3, high + 3); CHKERRQ(ierr);
238a7e14dcfSSatish Balay   ierr = VecGetOwnershipRange(FB, low + 4, high + 4); CHKERRQ(ierr);
239a7e14dcfSSatish Balay 
240a7e14dcfSSatish Balay   for (i = 1; i < 4; ++i) {
241a7e14dcfSSatish Balay     if (low[0] != low[i] || high[0] != high[i])
242a7e14dcfSSatish Balay       SETERRQ(PETSC_COMM_SELF,1,"Vectors must be identically loaded over processors");
243a7e14dcfSSatish Balay   }
244a7e14dcfSSatish Balay 
245a7e14dcfSSatish Balay   ierr = VecGetArray(X, &x); CHKERRQ(ierr);
246a7e14dcfSSatish Balay   ierr = VecGetArray(F, &f); CHKERRQ(ierr);
247a7e14dcfSSatish Balay   ierr = VecGetArray(L, &l); CHKERRQ(ierr);
248a7e14dcfSSatish Balay   ierr = VecGetArray(U, &u); CHKERRQ(ierr);
249a7e14dcfSSatish Balay   ierr = VecGetArray(FB, &fb); CHKERRQ(ierr);
250a7e14dcfSSatish Balay 
251a7e14dcfSSatish Balay   ierr = VecGetLocalSize(X, &n); CHKERRQ(ierr);
252a7e14dcfSSatish Balay 
253a7e14dcfSSatish Balay   for (i = 0; i < n; ++i) {
254a7e14dcfSSatish Balay     xval = x[i]; fval = f[i];
255a7e14dcfSSatish Balay     lval = l[i]; uval = u[i];
256a7e14dcfSSatish Balay 
257a7e14dcfSSatish Balay     if ((lval <= -TAO_INFINITY) && (uval >= TAO_INFINITY)) {
258a7e14dcfSSatish Balay       fb[i] = -fval;
259a7e14dcfSSatish Balay     }
260a7e14dcfSSatish Balay     else if (lval <= -TAO_INFINITY) {
261a7e14dcfSSatish Balay       fb[i] = -Fischer(uval - xval, -fval);
262a7e14dcfSSatish Balay     }
263a7e14dcfSSatish Balay     else if (uval >=  TAO_INFINITY) {
264a7e14dcfSSatish Balay       fb[i] =  Fischer(xval - lval,  fval);
265a7e14dcfSSatish Balay     }
266a7e14dcfSSatish Balay     else if (lval == uval) {
267a7e14dcfSSatish Balay       fb[i] = lval - xval;
268a7e14dcfSSatish Balay     }
269a7e14dcfSSatish Balay     else {
270a7e14dcfSSatish Balay       fval  =  Fischer(uval - xval, -fval);
271a7e14dcfSSatish Balay       fb[i] =  Fischer(xval - lval,  fval);
272a7e14dcfSSatish Balay     }
273a7e14dcfSSatish Balay   }
274a7e14dcfSSatish Balay 
275a7e14dcfSSatish Balay   ierr = VecRestoreArray(X, &x); CHKERRQ(ierr);
276a7e14dcfSSatish Balay   ierr = VecRestoreArray(F, &f); CHKERRQ(ierr);
277a7e14dcfSSatish Balay   ierr = VecRestoreArray(L, &l); CHKERRQ(ierr);
278a7e14dcfSSatish Balay   ierr = VecRestoreArray(U, &u); CHKERRQ(ierr);
279a7e14dcfSSatish Balay   ierr = VecRestoreArray(FB, &fb); CHKERRQ(ierr);
280a7e14dcfSSatish Balay 
281a7e14dcfSSatish Balay   PetscFunctionReturn(0);
282a7e14dcfSSatish Balay }
283a7e14dcfSSatish Balay 
284a7e14dcfSSatish Balay PETSC_STATIC_INLINE PetscReal SFischer(PetscReal a, PetscReal b, PetscReal c)
285a7e14dcfSSatish Balay {
286a7e14dcfSSatish Balay   /* Method suggested by Bob Vanderbei */
287a7e14dcfSSatish Balay    if (a + b <= 0) {
288a7e14dcfSSatish Balay      return PetscSqrtScalar(a*a + b*b + 2.0*c*c) - (a + b);
289a7e14dcfSSatish Balay    }
290a7e14dcfSSatish Balay    return 2.0*(c*c - a*b) / (PetscSqrtScalar(a*a + b*b + 2.0*c*c) + (a + b));
291a7e14dcfSSatish Balay }
292a7e14dcfSSatish Balay 
293a7e14dcfSSatish Balay #undef __FUNCT__
294a7e14dcfSSatish Balay #define __FUNCT__ "VecSFischer"
295a7e14dcfSSatish Balay /*@
296a7e14dcfSSatish Balay    VecSFischer - Evaluates the Smoothed Fischer-Burmeister function for
297a7e14dcfSSatish Balay    complementarity problems.
298a7e14dcfSSatish Balay 
299a7e14dcfSSatish Balay    Logically Collective on vectors
300a7e14dcfSSatish Balay 
301a7e14dcfSSatish Balay    Input Parameters:
302a7e14dcfSSatish Balay +  X - current point
303a7e14dcfSSatish Balay .  F - function evaluated at x
304a7e14dcfSSatish Balay .  L - lower bounds
305a7e14dcfSSatish Balay .  U - upper bounds
306a7e14dcfSSatish Balay -  mu - smoothing parameter
307a7e14dcfSSatish Balay 
308a7e14dcfSSatish Balay    Output Parameters:
309a7e14dcfSSatish Balay .  FB - The Smoothed Fischer-Burmeister function vector
310a7e14dcfSSatish Balay 
311a7e14dcfSSatish Balay    Notes:
312a7e14dcfSSatish Balay    The Smoothed Fischer-Burmeister function is defined as
313a7e14dcfSSatish Balay $        phi(a,b) := sqrt(a*a + b*b + 2*mu*mu) - a - b
314a7e14dcfSSatish Balay    and is used reformulate a complementarity problem as a semismooth
315a7e14dcfSSatish Balay    system of equations.
316a7e14dcfSSatish Balay 
317a7e14dcfSSatish Balay    The result of this function is done by cases:
318a7e14dcfSSatish Balay +  l[i] == -infinity, u[i] == infinity  -- fb[i] = -f[i] - 2*mu*x[i]
319a7e14dcfSSatish Balay .  l[i] == -infinity, u[i] finite       -- fb[i] = phi(u[i]-x[i], -f[i], mu)
320a7e14dcfSSatish Balay .  l[i] finite,       u[i] == infinity  -- fb[i] = phi(x[i]-l[i],  f[i], mu)
321a7e14dcfSSatish Balay .  l[i] finite < u[i] finite -- fb[i] = phi(x[i]-l[i], phi(u[i]-x[i], -f[u], mu), mu)
322a7e14dcfSSatish Balay -  otherwise l[i] == u[i] -- fb[i] = l[i] - x[i]
323a7e14dcfSSatish Balay 
324a7e14dcfSSatish Balay    Level: developer
325a7e14dcfSSatish Balay 
326a7e14dcfSSatish Balay .seealso  VecFischer()
327a7e14dcfSSatish Balay @*/
328a7e14dcfSSatish Balay PetscErrorCode VecSFischer(Vec X, Vec F, Vec L, Vec U, PetscReal mu, Vec FB)
329a7e14dcfSSatish Balay {
330a7e14dcfSSatish Balay   PetscReal *x, *f, *l, *u, *fb;
331a7e14dcfSSatish Balay   PetscReal xval, fval, lval, uval;
332a7e14dcfSSatish Balay   PetscErrorCode ierr;
333a7e14dcfSSatish Balay   PetscInt low[5], high[5], n, i;
334a7e14dcfSSatish Balay 
335a7e14dcfSSatish Balay   PetscFunctionBegin;
336a7e14dcfSSatish Balay   PetscValidHeaderSpecific(X, VEC_CLASSID,1);
337a7e14dcfSSatish Balay   PetscValidHeaderSpecific(F, VEC_CLASSID,2);
338a7e14dcfSSatish Balay   PetscValidHeaderSpecific(L, VEC_CLASSID,3);
339a7e14dcfSSatish Balay   PetscValidHeaderSpecific(U, VEC_CLASSID,4);
340a7e14dcfSSatish Balay   PetscValidHeaderSpecific(FB, VEC_CLASSID,6);
341a7e14dcfSSatish Balay 
342a7e14dcfSSatish Balay   ierr = VecGetOwnershipRange(X, low, high); CHKERRQ(ierr);
343a7e14dcfSSatish Balay   ierr = VecGetOwnershipRange(F, low + 1, high + 1); CHKERRQ(ierr);
344a7e14dcfSSatish Balay   ierr = VecGetOwnershipRange(L, low + 2, high + 2); CHKERRQ(ierr);
345a7e14dcfSSatish Balay   ierr = VecGetOwnershipRange(U, low + 3, high + 3); CHKERRQ(ierr);
346a7e14dcfSSatish Balay   ierr = VecGetOwnershipRange(FB, low + 4, high + 4); CHKERRQ(ierr);
347a7e14dcfSSatish Balay 
348a7e14dcfSSatish Balay   for (i = 1; i < 4; ++i) {
349a7e14dcfSSatish Balay     if (low[0] != low[i] || high[0] != high[i])
350a7e14dcfSSatish Balay       SETERRQ(PETSC_COMM_SELF,1,"Vectors must be identically loaded over processors");
351a7e14dcfSSatish Balay   }
352a7e14dcfSSatish Balay 
353a7e14dcfSSatish Balay   ierr = VecGetArray(X, &x); CHKERRQ(ierr);
354a7e14dcfSSatish Balay   ierr = VecGetArray(F, &f); CHKERRQ(ierr);
355a7e14dcfSSatish Balay   ierr = VecGetArray(L, &l); CHKERRQ(ierr);
356a7e14dcfSSatish Balay   ierr = VecGetArray(U, &u); CHKERRQ(ierr);
357a7e14dcfSSatish Balay   ierr = VecGetArray(FB, &fb); CHKERRQ(ierr);
358a7e14dcfSSatish Balay 
359a7e14dcfSSatish Balay   ierr = VecGetLocalSize(X, &n); CHKERRQ(ierr);
360a7e14dcfSSatish Balay 
361a7e14dcfSSatish Balay   for (i = 0; i < n; ++i) {
362a7e14dcfSSatish Balay     xval = (*x++); fval = (*f++);
363a7e14dcfSSatish Balay     lval = (*l++); uval = (*u++);
364a7e14dcfSSatish Balay 
365a7e14dcfSSatish Balay     if ((lval <= -TAO_INFINITY) && (uval >= TAO_INFINITY)) {
366a7e14dcfSSatish Balay       (*fb++) = -fval - mu*xval;
367a7e14dcfSSatish Balay     }
368a7e14dcfSSatish Balay     else if (lval <= -TAO_INFINITY) {
369a7e14dcfSSatish Balay       (*fb++) = -SFischer(uval - xval, -fval, mu);
370a7e14dcfSSatish Balay     }
371a7e14dcfSSatish Balay     else if (uval >=  TAO_INFINITY) {
372a7e14dcfSSatish Balay       (*fb++) =  SFischer(xval - lval,  fval, mu);
373a7e14dcfSSatish Balay     }
374a7e14dcfSSatish Balay     else if (lval == uval) {
375a7e14dcfSSatish Balay       (*fb++) = lval - xval;
376a7e14dcfSSatish Balay     }
377a7e14dcfSSatish Balay     else {
378a7e14dcfSSatish Balay       fval    =  SFischer(uval - xval, -fval, mu);
379a7e14dcfSSatish Balay       (*fb++) =  SFischer(xval - lval,  fval, mu);
380a7e14dcfSSatish Balay     }
381a7e14dcfSSatish Balay   }
382a7e14dcfSSatish Balay   x -= n; f -= n; l -=n; u -= n; fb -= n;
383a7e14dcfSSatish Balay 
384a7e14dcfSSatish Balay   ierr = VecRestoreArray(X, &x); CHKERRQ(ierr);
385a7e14dcfSSatish Balay   ierr = VecRestoreArray(F, &f); CHKERRQ(ierr);
386a7e14dcfSSatish Balay   ierr = VecRestoreArray(L, &l); CHKERRQ(ierr);
387a7e14dcfSSatish Balay   ierr = VecRestoreArray(U, &u); CHKERRQ(ierr);
388a7e14dcfSSatish Balay   ierr = VecRestoreArray(FB, &fb); CHKERRQ(ierr);
389a7e14dcfSSatish Balay   PetscFunctionReturn(0);
390a7e14dcfSSatish Balay }
391a7e14dcfSSatish Balay 
392a7e14dcfSSatish Balay PETSC_STATIC_INLINE PetscReal fischnorm(PetscReal a, PetscReal b)
393a7e14dcfSSatish Balay {
394a7e14dcfSSatish Balay   return PetscSqrtScalar(a*a + b*b);
395a7e14dcfSSatish Balay }
396a7e14dcfSSatish Balay 
397a7e14dcfSSatish Balay PETSC_STATIC_INLINE PetscReal fischsnorm(PetscReal a, PetscReal b, PetscReal c)
398a7e14dcfSSatish Balay {
399a7e14dcfSSatish Balay   return PetscSqrtScalar(a*a + b*b + 2.0*c*c);
400a7e14dcfSSatish Balay }
401a7e14dcfSSatish Balay 
402a7e14dcfSSatish Balay #undef __FUNCT__
403a7e14dcfSSatish Balay #define __FUNCT__ "D_Fischer"
404a7e14dcfSSatish Balay /*@
405a7e14dcfSSatish Balay    D_Fischer - Calculates an element of the B-subdifferential of the
406a7e14dcfSSatish Balay    Fischer-Burmeister function for complementarity problems.
407a7e14dcfSSatish Balay 
408a7e14dcfSSatish Balay    Collective on jac
409a7e14dcfSSatish Balay 
410a7e14dcfSSatish Balay    Input Parameters:
411a7e14dcfSSatish Balay +  jac - the jacobian of f at X
412a7e14dcfSSatish Balay .  X - current point
413a7e14dcfSSatish Balay .  Con - constraints function evaluated at X
414a7e14dcfSSatish Balay .  XL - lower bounds
415a7e14dcfSSatish Balay .  XU - upper bounds
416a7e14dcfSSatish Balay .  t1 - work vector
417a7e14dcfSSatish Balay -  t2 - work vector
418a7e14dcfSSatish Balay 
419a7e14dcfSSatish Balay    Output Parameters:
420a7e14dcfSSatish Balay +  Da - diagonal perturbation component of the result
421a7e14dcfSSatish Balay -  Db - row scaling component of the result
422a7e14dcfSSatish Balay 
423a7e14dcfSSatish Balay    Level: developer
424a7e14dcfSSatish Balay 
425a7e14dcfSSatish Balay .seealso: VecFischer()
426a7e14dcfSSatish Balay @*/
427a7e14dcfSSatish Balay PetscErrorCode D_Fischer(Mat jac, Vec X, Vec Con, Vec XL, Vec XU,
428a7e14dcfSSatish Balay 		      Vec T1, Vec T2, Vec Da, Vec Db)
429a7e14dcfSSatish Balay {
430a7e14dcfSSatish Balay   PetscErrorCode ierr;
431a7e14dcfSSatish Balay   PetscInt i,nn;
432a7e14dcfSSatish Balay   PetscReal *x,*f,*l,*u,*da,*db,*t1,*t2;
433a7e14dcfSSatish Balay   PetscReal ai,bi,ci,di,ei;
434a7e14dcfSSatish Balay 
435a7e14dcfSSatish Balay   PetscFunctionBegin;
436a7e14dcfSSatish Balay 
437a7e14dcfSSatish Balay   ierr = VecGetLocalSize(X,&nn); CHKERRQ(ierr);
438a7e14dcfSSatish Balay 
439a7e14dcfSSatish Balay   ierr = VecGetArray(X,&x);CHKERRQ(ierr);
440a7e14dcfSSatish Balay   ierr = VecGetArray(Con,&f);CHKERRQ(ierr);
441a7e14dcfSSatish Balay   ierr = VecGetArray(XL,&l);CHKERRQ(ierr);
442a7e14dcfSSatish Balay   ierr = VecGetArray(XU,&u);CHKERRQ(ierr);
443a7e14dcfSSatish Balay   ierr = VecGetArray(Da,&da);CHKERRQ(ierr);
444a7e14dcfSSatish Balay   ierr = VecGetArray(Db,&db);CHKERRQ(ierr);
445a7e14dcfSSatish Balay   ierr = VecGetArray(T1,&t1);CHKERRQ(ierr);
446a7e14dcfSSatish Balay   ierr = VecGetArray(T2,&t2);CHKERRQ(ierr);
447a7e14dcfSSatish Balay 
448a7e14dcfSSatish Balay   for (i = 0; i < nn; i++) {
449a7e14dcfSSatish Balay     da[i] = 0;
450a7e14dcfSSatish Balay     db[i] = 0;
451a7e14dcfSSatish Balay     t1[i] = 0;
452a7e14dcfSSatish Balay 
453a7e14dcfSSatish Balay     if (PetscAbsReal(f[i]) <= PETSC_MACHINE_EPSILON) {
454a7e14dcfSSatish Balay       if (l[i] > TAO_NINFINITY && PetscAbsReal(x[i] - l[i]) <= PETSC_MACHINE_EPSILON) {
455a7e14dcfSSatish Balay         t1[i] = 1;
456a7e14dcfSSatish Balay         da[i] = 1;
457a7e14dcfSSatish Balay       }
458a7e14dcfSSatish Balay 
459a7e14dcfSSatish Balay       if (u[i] <  TAO_INFINITY && PetscAbsReal(u[i] - x[i]) <= PETSC_MACHINE_EPSILON) {
460a7e14dcfSSatish Balay         t1[i] = 1;
461a7e14dcfSSatish Balay         db[i] = 1;
462a7e14dcfSSatish Balay       }
463a7e14dcfSSatish Balay     }
464a7e14dcfSSatish Balay   }
465a7e14dcfSSatish Balay 
466a7e14dcfSSatish Balay   ierr = VecRestoreArray(T1,&t1); CHKERRQ(ierr);
467a7e14dcfSSatish Balay   ierr = VecRestoreArray(T2,&t2); CHKERRQ(ierr);
468a7e14dcfSSatish Balay   ierr = MatMult(jac,T1,T2); CHKERRQ(ierr);
469a7e14dcfSSatish Balay   ierr = VecGetArray(T2,&t2); CHKERRQ(ierr);
470a7e14dcfSSatish Balay 
471a7e14dcfSSatish Balay   for (i = 0; i < nn; i++) {
472a7e14dcfSSatish Balay     if ((l[i] <= TAO_NINFINITY) && (u[i] >= TAO_INFINITY)) {
473a7e14dcfSSatish Balay       da[i] = 0;
474a7e14dcfSSatish Balay       db[i] = -1;
475a7e14dcfSSatish Balay     }
476a7e14dcfSSatish Balay     else if (l[i] <= TAO_NINFINITY) {
477a7e14dcfSSatish Balay       if (db[i] >= 1) {
478a7e14dcfSSatish Balay         ai = fischnorm(1, t2[i]);
479a7e14dcfSSatish Balay 
480a7e14dcfSSatish Balay         da[i] = -1/ai - 1;
481a7e14dcfSSatish Balay         db[i] = -t2[i]/ai - 1;
482a7e14dcfSSatish Balay       }
483a7e14dcfSSatish Balay       else {
484a7e14dcfSSatish Balay         bi = u[i] - x[i];
485a7e14dcfSSatish Balay         ai = fischnorm(bi, f[i]);
486a7e14dcfSSatish Balay         ai = PetscMax(PETSC_MACHINE_EPSILON, ai);
487a7e14dcfSSatish Balay 
488a7e14dcfSSatish Balay         da[i] = bi / ai - 1;
489a7e14dcfSSatish Balay         db[i] = -f[i] / ai - 1;
490a7e14dcfSSatish Balay       }
491a7e14dcfSSatish Balay     }
492a7e14dcfSSatish Balay     else if (u[i] >=  TAO_INFINITY) {
493a7e14dcfSSatish Balay       if (da[i] >= 1) {
494a7e14dcfSSatish Balay         ai = fischnorm(1, t2[i]);
495a7e14dcfSSatish Balay 
496a7e14dcfSSatish Balay         da[i] = 1 / ai - 1;
497a7e14dcfSSatish Balay         db[i] = t2[i] / ai - 1;
498a7e14dcfSSatish Balay       }
499a7e14dcfSSatish Balay       else {
500a7e14dcfSSatish Balay         bi = x[i] - l[i];
501a7e14dcfSSatish Balay         ai = fischnorm(bi, f[i]);
502a7e14dcfSSatish Balay         ai = PetscMax(PETSC_MACHINE_EPSILON, ai);
503a7e14dcfSSatish Balay 
504a7e14dcfSSatish Balay         da[i] = bi / ai - 1;
505a7e14dcfSSatish Balay         db[i] = f[i] / ai - 1;
506a7e14dcfSSatish Balay       }
507a7e14dcfSSatish Balay     }
508a7e14dcfSSatish Balay     else if (l[i] == u[i]) {
509a7e14dcfSSatish Balay       da[i] = -1;
510a7e14dcfSSatish Balay       db[i] = 0;
511a7e14dcfSSatish Balay     }
512a7e14dcfSSatish Balay     else {
513a7e14dcfSSatish Balay       if (db[i] >= 1) {
514a7e14dcfSSatish Balay         ai = fischnorm(1, t2[i]);
515a7e14dcfSSatish Balay 
516a7e14dcfSSatish Balay         ci = 1 / ai + 1;
517a7e14dcfSSatish Balay         di = t2[i] / ai + 1;
518a7e14dcfSSatish Balay       }
519a7e14dcfSSatish Balay       else {
520a7e14dcfSSatish Balay         bi = x[i] - u[i];
521a7e14dcfSSatish Balay         ai = fischnorm(bi, f[i]);
522a7e14dcfSSatish Balay         ai = PetscMax(PETSC_MACHINE_EPSILON, ai);
523a7e14dcfSSatish Balay 
524a7e14dcfSSatish Balay         ci = bi / ai + 1;
525a7e14dcfSSatish Balay         di = f[i] / ai + 1;
526a7e14dcfSSatish Balay       }
527a7e14dcfSSatish Balay 
528a7e14dcfSSatish Balay       if (da[i] >= 1) {
529a7e14dcfSSatish Balay         bi = ci + di*t2[i];
530a7e14dcfSSatish Balay         ai = fischnorm(1, bi);
531a7e14dcfSSatish Balay 
532a7e14dcfSSatish Balay         bi = bi / ai - 1;
533a7e14dcfSSatish Balay         ai = 1 / ai - 1;
534a7e14dcfSSatish Balay       }
535a7e14dcfSSatish Balay       else {
536a7e14dcfSSatish Balay         ei = Fischer(u[i] - x[i], -f[i]);
537a7e14dcfSSatish Balay         ai = fischnorm(x[i] - l[i], ei);
538a7e14dcfSSatish Balay         ai = PetscMax(PETSC_MACHINE_EPSILON, ai);
539a7e14dcfSSatish Balay 
540a7e14dcfSSatish Balay         bi = ei / ai - 1;
541a7e14dcfSSatish Balay         ai = (x[i] - l[i]) / ai - 1;
542a7e14dcfSSatish Balay       }
543a7e14dcfSSatish Balay 
544a7e14dcfSSatish Balay       da[i] = ai + bi*ci;
545a7e14dcfSSatish Balay       db[i] = bi*di;
546a7e14dcfSSatish Balay     }
547a7e14dcfSSatish Balay   }
548a7e14dcfSSatish Balay 
549a7e14dcfSSatish Balay   ierr = VecRestoreArray(Da,&da); CHKERRQ(ierr);
550a7e14dcfSSatish Balay   ierr = VecRestoreArray(Db,&db); CHKERRQ(ierr);
551a7e14dcfSSatish Balay   ierr = VecRestoreArray(X,&x); CHKERRQ(ierr);
552a7e14dcfSSatish Balay   ierr = VecRestoreArray(Con,&f); CHKERRQ(ierr);
553a7e14dcfSSatish Balay   ierr = VecRestoreArray(XL,&l); CHKERRQ(ierr);
554a7e14dcfSSatish Balay   ierr = VecRestoreArray(XU,&u); CHKERRQ(ierr);
555a7e14dcfSSatish Balay   ierr = VecRestoreArray(T2,&t2); CHKERRQ(ierr);
556a7e14dcfSSatish Balay   PetscFunctionReturn(0);
557*8e3154b5SSatish Balay }
558a7e14dcfSSatish Balay 
559a7e14dcfSSatish Balay #undef __FUNCT__
560a7e14dcfSSatish Balay #define __FUNCT__ "D_SFischer"
561a7e14dcfSSatish Balay /*@
562a7e14dcfSSatish Balay    D_SFischer - Calculates an element of the B-subdifferential of the
563a7e14dcfSSatish Balay    smoothed Fischer-Burmeister function for complementarity problems.
564a7e14dcfSSatish Balay 
565a7e14dcfSSatish Balay    Collective on jac
566a7e14dcfSSatish Balay 
567a7e14dcfSSatish Balay    Input Parameters:
568a7e14dcfSSatish Balay +  jac - the jacobian of f at X
569a7e14dcfSSatish Balay .  X - current point
570a7e14dcfSSatish Balay .  F - constraint function evaluated at X
571a7e14dcfSSatish Balay .  XL - lower bounds
572a7e14dcfSSatish Balay .  XU - upper bounds
573a7e14dcfSSatish Balay .  mu - smoothing parameter
574a7e14dcfSSatish Balay .  T1 - work vector
575a7e14dcfSSatish Balay -  T2 - work vector
576a7e14dcfSSatish Balay 
577a7e14dcfSSatish Balay    Output Parameter:
578a7e14dcfSSatish Balay +  Da - diagonal perturbation component of the result
579a7e14dcfSSatish Balay .  Db - row scaling component of the result
580a7e14dcfSSatish Balay -  Dm - derivative with respect to scaling parameter
581a7e14dcfSSatish Balay 
582a7e14dcfSSatish Balay    Level: developer
583a7e14dcfSSatish Balay 
584a7e14dcfSSatish Balay .seealso D_Fischer()
585a7e14dcfSSatish Balay @*/
586a7e14dcfSSatish Balay PetscErrorCode D_SFischer(Mat jac, Vec X, Vec Con,
587a7e14dcfSSatish Balay                        Vec XL, Vec XU, PetscReal mu,
588a7e14dcfSSatish Balay                        Vec T1, Vec T2,
589a7e14dcfSSatish Balay                        Vec Da, Vec Db, Vec Dm)
590a7e14dcfSSatish Balay {
591a7e14dcfSSatish Balay   PetscErrorCode ierr;
592a7e14dcfSSatish Balay   PetscInt i,nn;
593a7e14dcfSSatish Balay   PetscReal *x, *f, *l, *u, *da, *db, *dm;
594a7e14dcfSSatish Balay   PetscReal ai, bi, ci, di, ei, fi;
595a7e14dcfSSatish Balay 
596a7e14dcfSSatish Balay   PetscFunctionBegin;
597a7e14dcfSSatish Balay 
598a7e14dcfSSatish Balay   if (PetscAbsReal(mu) <= PETSC_MACHINE_EPSILON) {
599a7e14dcfSSatish Balay     ierr = VecZeroEntries(Dm); CHKERRQ(ierr);
600a7e14dcfSSatish Balay     ierr = D_Fischer(jac, X, Con, XL, XU, T1, T2, Da, Db); CHKERRQ(ierr);
601a7e14dcfSSatish Balay   }
602a7e14dcfSSatish Balay   else {
603a7e14dcfSSatish Balay     ierr = VecGetLocalSize(X,&nn); CHKERRQ(ierr);
604a7e14dcfSSatish Balay     ierr = VecGetArray(X,&x); CHKERRQ(ierr);
605a7e14dcfSSatish Balay     ierr = VecGetArray(Con,&f); CHKERRQ(ierr);
606a7e14dcfSSatish Balay     ierr = VecGetArray(XL,&l); CHKERRQ(ierr);
607a7e14dcfSSatish Balay     ierr = VecGetArray(XU,&u); CHKERRQ(ierr);
608a7e14dcfSSatish Balay     ierr = VecGetArray(Da,&da); CHKERRQ(ierr);
609a7e14dcfSSatish Balay     ierr = VecGetArray(Db,&db); CHKERRQ(ierr);
610a7e14dcfSSatish Balay     ierr = VecGetArray(Dm,&dm); CHKERRQ(ierr);
611a7e14dcfSSatish Balay 
612a7e14dcfSSatish Balay     for (i = 0; i < nn; ++i) {
613a7e14dcfSSatish Balay       if ((l[i] <= TAO_NINFINITY) && (u[i] >= TAO_INFINITY)) {
614a7e14dcfSSatish Balay         da[i] = -mu;
615a7e14dcfSSatish Balay         db[i] = -1;
616a7e14dcfSSatish Balay         dm[i] = -x[i];
617a7e14dcfSSatish Balay       }
618a7e14dcfSSatish Balay       else if (l[i] <= TAO_NINFINITY) {
619a7e14dcfSSatish Balay         bi = u[i] - x[i];
620a7e14dcfSSatish Balay         ai = fischsnorm(bi, f[i], mu);
621a7e14dcfSSatish Balay         ai = PetscMax(PETSC_MACHINE_EPSILON, ai);
622a7e14dcfSSatish Balay 
623a7e14dcfSSatish Balay         da[i] = bi / ai - 1;
624a7e14dcfSSatish Balay         db[i] = -f[i] / ai - 1;
625a7e14dcfSSatish Balay         dm[i] = 2.0 * mu / ai;
626a7e14dcfSSatish Balay       }
627a7e14dcfSSatish Balay       else if (u[i] >=  TAO_INFINITY) {
628a7e14dcfSSatish Balay         bi = x[i] - l[i];
629a7e14dcfSSatish Balay         ai = fischsnorm(bi, f[i], mu);
630a7e14dcfSSatish Balay         ai = PetscMax(PETSC_MACHINE_EPSILON, ai);
631a7e14dcfSSatish Balay 
632a7e14dcfSSatish Balay         da[i] = bi / ai - 1;
633a7e14dcfSSatish Balay         db[i] = f[i] / ai - 1;
634a7e14dcfSSatish Balay         dm[i] = 2.0 * mu / ai;
635a7e14dcfSSatish Balay       }
636a7e14dcfSSatish Balay       else if (l[i] == u[i]) {
637a7e14dcfSSatish Balay         da[i] = -1;
638a7e14dcfSSatish Balay         db[i] = 0;
639a7e14dcfSSatish Balay         dm[i] = 0;
640a7e14dcfSSatish Balay       }
641a7e14dcfSSatish Balay       else {
642a7e14dcfSSatish Balay         bi = x[i] - u[i];
643a7e14dcfSSatish Balay         ai = fischsnorm(bi, f[i], mu);
644a7e14dcfSSatish Balay         ai = PetscMax(PETSC_MACHINE_EPSILON, ai);
645a7e14dcfSSatish Balay 
646a7e14dcfSSatish Balay         ci = bi / ai + 1;
647a7e14dcfSSatish Balay         di = f[i] / ai + 1;
648a7e14dcfSSatish Balay         fi = 2.0 * mu / ai;
649a7e14dcfSSatish Balay 
650a7e14dcfSSatish Balay         ei = SFischer(u[i] - x[i], -f[i], mu);
651a7e14dcfSSatish Balay         ai = fischsnorm(x[i] - l[i], ei, mu);
652a7e14dcfSSatish Balay         ai = PetscMax(PETSC_MACHINE_EPSILON, ai);
653a7e14dcfSSatish Balay 
654a7e14dcfSSatish Balay         bi = ei / ai - 1;
655a7e14dcfSSatish Balay         ei = 2.0 * mu / ei;
656a7e14dcfSSatish Balay         ai = (x[i] - l[i]) / ai - 1;
657a7e14dcfSSatish Balay 
658a7e14dcfSSatish Balay         da[i] = ai + bi*ci;
659a7e14dcfSSatish Balay         db[i] = bi*di;
660a7e14dcfSSatish Balay         dm[i] = ei + bi*fi;
661a7e14dcfSSatish Balay       }
662a7e14dcfSSatish Balay     }
663a7e14dcfSSatish Balay 
664a7e14dcfSSatish Balay     ierr = VecRestoreArray(X,&x); CHKERRQ(ierr);
665a7e14dcfSSatish Balay     ierr = VecRestoreArray(Con,&f); CHKERRQ(ierr);
666a7e14dcfSSatish Balay     ierr = VecRestoreArray(XL,&l); CHKERRQ(ierr);
667a7e14dcfSSatish Balay     ierr = VecRestoreArray(XU,&u); CHKERRQ(ierr);
668a7e14dcfSSatish Balay     ierr = VecRestoreArray(Da,&da); CHKERRQ(ierr);
669a7e14dcfSSatish Balay     ierr = VecRestoreArray(Db,&db); CHKERRQ(ierr);
670a7e14dcfSSatish Balay     ierr = VecRestoreArray(Dm,&dm); CHKERRQ(ierr);
671a7e14dcfSSatish Balay 
672a7e14dcfSSatish Balay   }
673a7e14dcfSSatish Balay   PetscFunctionReturn(0);
674a7e14dcfSSatish Balay }
675a7e14dcfSSatish Balay 
676