1 2 #include <petsc/private/viewerimpl.h> /*I "petscsys.h" I*/ 3 4 typedef struct { 5 char *string; /* string where info is stored */ 6 char *head; /* pointer to begining of unused portion */ 7 size_t curlen,maxlen; 8 PetscBool ownstring; /* string viewer is responsable for freeing the string */ 9 } PetscViewer_String; 10 11 static PetscErrorCode PetscViewerDestroy_String(PetscViewer viewer) 12 { 13 PetscViewer_String *vstr = (PetscViewer_String*)viewer->data; 14 PetscErrorCode ierr; 15 16 PetscFunctionBegin; 17 if (vstr->ownstring) { 18 ierr = PetscFree(vstr->string);CHKERRQ(ierr); 19 } 20 ierr = PetscFree(vstr);CHKERRQ(ierr); 21 PetscFunctionReturn(0); 22 } 23 24 /*@C 25 PetscViewerStringSPrintf - Prints information to a PetscViewer string. 26 27 Logically Collective on PetscViewer (Hmmm, each processor maintains a separate string) 28 29 Input Parameters: 30 + v - a string PetscViewer, formed by PetscViewerStringOpen() 31 - format - the format of the input 32 33 Level: developer 34 35 Fortran Note: 36 This routine is not supported in Fortran. 37 38 Concepts: printing^to string 39 40 .seealso: PetscViewerStringOpen(), PetscViewerStringGetStringRead(), PetscViewerStringSetString(), PETSCVIEWERSTRING 41 @*/ 42 PetscErrorCode PetscViewerStringSPrintf(PetscViewer viewer,const char format[],...) 43 { 44 va_list Argp; 45 size_t fullLength; 46 size_t shift,cshift; 47 PetscErrorCode ierr; 48 PetscBool isstring; 49 char tmp[4096]; 50 PetscViewer_String *vstr = (PetscViewer_String*)viewer->data; 51 52 PetscFunctionBegin; 53 PetscValidHeaderSpecific(viewer,PETSC_VIEWER_CLASSID,1); 54 PetscValidCharPointer(format,2); 55 ierr = PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERSTRING,&isstring);CHKERRQ(ierr); 56 if (!isstring) PetscFunctionReturn(0); 57 if (!vstr->string) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ORDER,"Must call PetscViewerStringSetString() before using"); 58 59 va_start(Argp,format); 60 ierr = PetscVSNPrintf(tmp,4096,format,&fullLength,Argp);CHKERRQ(ierr); 61 va_end(Argp); 62 ierr = PetscStrlen(tmp,&shift);CHKERRQ(ierr); 63 cshift = shift+1; 64 if (cshift >= vstr->maxlen - vstr->curlen - 1) cshift = vstr->maxlen - vstr->curlen - 1; 65 ierr = PetscStrncpy(vstr->head,tmp,cshift);CHKERRQ(ierr); 66 vstr->head += shift; 67 vstr->curlen += shift; 68 PetscFunctionReturn(0); 69 } 70 71 /*@C 72 PetscViewerStringOpen - Opens a string as a PetscViewer. This is a very 73 simple PetscViewer; information on the object is simply stored into 74 the string in a fairly nice way. 75 76 Collective on MPI_Comm 77 78 Input Parameters: 79 + comm - the communicator 80 . string - the string to use 81 - len - the string length 82 83 Output Parameter: 84 . lab - the PetscViewer 85 86 Level: advanced 87 88 Fortran Note: 89 This routine is not supported in Fortran. 90 91 Concepts: PetscViewerString^creating 92 93 .seealso: PetscViewerDestroy(), PetscViewerStringSPrintf(), PetscViewerStringGetStringRead(), PetscViewerStringSetString(), PETSCVIEWERSTRING 94 @*/ 95 PetscErrorCode PetscViewerStringOpen(MPI_Comm comm,char string[],size_t len,PetscViewer *lab) 96 { 97 PetscErrorCode ierr; 98 99 PetscFunctionBegin; 100 ierr = PetscViewerCreate(comm,lab);CHKERRQ(ierr); 101 ierr = PetscViewerSetType(*lab,PETSCVIEWERSTRING);CHKERRQ(ierr); 102 ierr = PetscViewerStringSetString(*lab,string,len);CHKERRQ(ierr); 103 PetscFunctionReturn(0); 104 } 105 106 PetscErrorCode PetscViewerGetSubViewer_String(PetscViewer viewer,MPI_Comm comm,PetscViewer *sviewer) 107 { 108 PetscViewer_String *vstr = (PetscViewer_String*)viewer->data; 109 PetscErrorCode ierr; 110 111 PetscFunctionBegin; 112 ierr = PetscViewerStringOpen(PETSC_COMM_SELF,vstr->head,vstr->maxlen-vstr->curlen,sviewer);CHKERRQ(ierr); 113 PetscFunctionReturn(0); 114 } 115 116 PetscErrorCode PetscViewerRestoreSubViewer_String(PetscViewer viewer,MPI_Comm comm,PetscViewer *sviewer) 117 { 118 PetscErrorCode ierr; 119 PetscViewer_String *iviewer = (PetscViewer_String*)(*sviewer)->data; 120 PetscViewer_String *vstr = (PetscViewer_String*)viewer->data; 121 122 PetscFunctionBegin; 123 vstr->head = iviewer->head; 124 vstr->curlen += iviewer->curlen; 125 ierr = PetscViewerDestroy(sviewer);CHKERRQ(ierr); 126 PetscFunctionReturn(0); 127 } 128 129 /*MC 130 PETSCVIEWERSTRING - A viewer that writes to a string 131 132 133 .seealso: PetscViewerStringOpen(), PetscViewerStringSPrintf(), PetscViewerSocketOpen(), PetscViewerDrawOpen(), PETSCVIEWERSOCKET, 134 PetscViewerCreate(), PetscViewerASCIIOpen(), PetscViewerBinaryOpen(), PETSCVIEWERBINARY, PETSCVIEWERDRAW, 135 PetscViewerMatlabOpen(), VecView(), DMView(), PetscViewerMatlabPutArray(), PETSCVIEWERASCII, PETSCVIEWERMATLAB, 136 PetscViewerFileSetName(), PetscViewerFileSetMode(), PetscViewerFormat, PetscViewerType, PetscViewerSetType() 137 138 Level: beginner 139 M*/ 140 141 PETSC_EXTERN PetscErrorCode PetscViewerCreate_String(PetscViewer v) 142 { 143 PetscViewer_String *vstr; 144 PetscErrorCode ierr; 145 146 PetscFunctionBegin; 147 v->ops->destroy = PetscViewerDestroy_String; 148 v->ops->view = 0; 149 v->ops->flush = 0; 150 v->ops->getsubviewer = PetscViewerGetSubViewer_String; 151 v->ops->restoresubviewer = PetscViewerRestoreSubViewer_String; 152 ierr = PetscNewLog(v,&vstr);CHKERRQ(ierr); 153 v->data = (void*)vstr; 154 vstr->string = 0; 155 PetscFunctionReturn(0); 156 } 157 158 /*@C 159 160 PetscViewerStringGetStringRead - Returns the string that a string viewer uses 161 162 Logically Collective on PetscViewer 163 164 Input Parameter: 165 . viewer - string viewer 166 167 Output Paramters: 168 + string - the string, optional use NULL if you do not need 169 - len - the length of the string, optional use NULL if you do 170 171 Notes: Do not write to the string nor free it 172 173 Level: advanced 174 175 .seealso: PetscViewerStringOpen(), PETSCVIEWERSTRING, PetscViewerStringSetString(), PetscViewerStringSPrintf(), 176 PetscViewerStringSetOwnString() 177 @*/ 178 PetscErrorCode PetscViewerStringGetStringRead(PetscViewer viewer,const char *string[],size_t *len) 179 { 180 PetscViewer_String *vstr = (PetscViewer_String*)viewer->data; 181 PetscErrorCode ierr; 182 PetscBool isstring; 183 184 PetscFunctionBegin; 185 PetscValidHeaderSpecific(viewer,PETSC_VIEWER_CLASSID,1); 186 ierr = PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERSTRING,&isstring);CHKERRQ(ierr); 187 if (!isstring) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_WRONG,"Only for PETSCVIEWERSTRING"); 188 if (string) *string = vstr->string; 189 if (len) *len = vstr->maxlen; 190 PetscFunctionReturn(0); 191 } 192 193 /*@C 194 195 PetscViewerStringSetString - sets the string that a string viewer will print to 196 197 Logically Collective on PetscViewer 198 199 Input Parameters: 200 + viewer - string viewer you wish to attach string to 201 . string - the string to print data into 202 - len - the length of the string 203 204 Notes: The function does not copy the string, it uses it directly therefor you cannot free 205 the string until the viewer is destroyed. If you call PetscViewerStringSetOwnString() the ownership 206 passes to the viewer and it will be responsable for freeing it. In this case the string must be 207 obtained with PetscMalloc(). 208 209 Level: advanced 210 211 .seealso: PetscViewerStringOpen(), PETSCVIEWERSTRING, PetscViewerStringGetStringRead(), PetscViewerStringSPrintf(), 212 PetscViewerStringSetOwnString() 213 @*/ 214 PetscErrorCode PetscViewerStringSetString(PetscViewer viewer,char string[],size_t len) 215 { 216 PetscViewer_String *vstr = (PetscViewer_String*)viewer->data; 217 PetscErrorCode ierr; 218 PetscBool isstring; 219 220 PetscFunctionBegin; 221 PetscValidHeaderSpecific(viewer,PETSC_VIEWER_CLASSID,1); 222 PetscValidCharPointer(string,2); 223 ierr = PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERSTRING,&isstring);CHKERRQ(ierr); 224 if (!isstring) PetscFunctionReturn(0); 225 if (len <= 2) SETERRQ(PETSC_COMM_SELF,PETSC_ERR_ARG_OUTOFRANGE,"String must have length at least 2"); 226 227 ierr = PetscMemzero(string,len*sizeof(char));CHKERRQ(ierr); 228 vstr->string = string; 229 vstr->head = string; 230 vstr->curlen = 0; 231 vstr->maxlen = len; 232 PetscFunctionReturn(0); 233 } 234 235 /*@C 236 237 PetscViewerStringSetOwnString - tells the viewer that it now owns the string and is responsible for freeing it 238 239 Logically Collective on PetscViewer 240 241 Input Parameters: 242 . viewer - string viewer 243 244 Notes: If you call this the string must have been obtained with PetscMalloc() and you cannot free the string 245 246 Level: advanced 247 248 .seealso: PetscViewerStringOpen(), PETSCVIEWERSTRING, PetscViewerStringGetStringRead(), PetscViewerStringSPrintf(), 249 PetscViewerStringSetString() 250 @*/ 251 PetscErrorCode PetscViewerStringSetOwnString(PetscViewer viewer) 252 { 253 PetscViewer_String *vstr = (PetscViewer_String*)viewer->data; 254 PetscErrorCode ierr; 255 PetscBool isstring; 256 257 PetscFunctionBegin; 258 PetscValidHeaderSpecific(viewer,PETSC_VIEWER_CLASSID,1); 259 ierr = PetscObjectTypeCompare((PetscObject)viewer,PETSCVIEWERSTRING,&isstring);CHKERRQ(ierr); 260 if (!isstring) PetscFunctionReturn(0); 261 262 vstr->ownstring = PETSC_TRUE; 263 PetscFunctionReturn(0); 264 } 265 266 267 268 269 270